无法选择复选框--它们是可编辑的!Java Swing

无法选择复选框--它们是可编辑的!Java Swing,java,swing,jtable,Java,Swing,Jtable,我在这个网站上看到了很多关于这个问题的问题,我不知道为什么它仍然不起作用 问题: 我制作了一个JTable,显示在JScrollPane中。JTable的构造如下: table = new JTable(new DataTableModel()); 如您所见,我使用了一个名为DataTableModel的自定义AbstractDataModel。现在,当我显示此时,会出现复选框,但无法选中它们。它们是可编辑的,如下所示。下面是DataTableModel类中的相关代码:(请注意,我的复选

我在这个网站上看到了很多关于这个问题的问题,我不知道为什么它仍然不起作用

问题:

我制作了一个
JTable
,显示在
JScrollPane
中。
JTable
的构造如下:

table = new JTable(new DataTableModel());   
如您所见,我使用了一个名为
DataTableModel
的自定义
AbstractDataModel
。现在,当我显示此时,会出现复选框,但无法选中它们。它们是可编辑的,如下所示。下面是
DataTableModel
类中的相关代码:(请注意,我的复选框列是索引0处的第一列,我的数组中该列的数据为“null”)。对一些人来说

public class DataTableModel extends AbstractTableModel
{
    private String[][] data;
    private String[] header =
    { "", "KB Name", "fpGUID" };

    public DataTableModel() throws SQLException
    {
        // ========= CONNECTS TO DB AND PULLS RESULTS ==========

        // GETS RESULTS SET CALLED "rs"

        // populate data array
        int counter = 0;
        while (rs.next())
        {
            //data[counter][0] = "sfsdfsdfs ";
            data[counter][1] = (String) rs.getObject(2);
            data[counter][2] = (String) rs.getObject(4);

            counter++;
        }
        // =====================================================

    }

@Override
public String getValueAt(int rowIndex, int columnIndex)
{
    return data[rowIndex][columnIndex];
}

public boolean isCellEditable(int row, int col)
{
    return col == 0;
}

public Class getColumnClass(int column)
{
    if (column == 0)
    {
        return Boolean.class;
    } else
    {
        return String.class;
    }
}

因此,我的
getColumnClass()
方法似乎很好,那么问题出在哪里呢?可能是我的“数据”中的什么东西,我将数据存储在表中。这是数据数组:

有很多东西跳出了

  • (正如贝京已经指出的)
    getValueAt
    似乎被宣布为错误。它应该返回
    对象
    。想一想。您的期望是第一列将是
    boolean
    ,因此如何从该方法返回
    String
    ,从而导致
  • 您的
    数据
    数组是一个
    字符串的数组
    …其中,第一个值应该是
    布尔值
    。现在您实际上可以保留该值,但您需要将值从
    getValueAt
    方法转换为
    boolean
    ,然后再次转换为
    setValueAt
    方法…这将导致
  • 您尚未实现
    setValueAt
    ,因此无法存储对单元格值的更改
  • 您也没有实现
    getRowCount
    ,这是必需的,
    getColumnCount
    ,这是必需的,您应该实现
    getColumnName
    ,因为您实际上有一些

现在,有一些方法可以绕过整个“第一列必须是布尔值”的问题,但坦率地说,这样做的代码要少得多

我还强烈建议您查看一下SwingWorker,并使用它来加载所有数据,否则您可能会发现,在开始加载数据时,UI会突然停止,这通常相当令人不快

看看


有关更多详细信息,请参见以下内容:

  • (正如贝京已经指出的)
    getValueAt
    似乎被宣布为错误。它应该返回
    对象
    。想一想。您的期望是第一列将是
    boolean
    ,因此如何从该方法返回
    String
    ,从而导致
  • 您的
    数据
    数组是一个
    字符串的数组
    …其中,第一个值应该是
    布尔值
    。现在您实际上可以保留该值,但您需要将值从
    getValueAt
    方法转换为
    boolean
    ,然后再次转换为
    setValueAt
    方法…这将导致
  • 您尚未实现
    setValueAt
    ,因此无法存储对单元格值的更改
  • 您也没有实现
    getRowCount
    ,这是必需的,
    getColumnCount
    ,这是必需的,您应该实现
    getColumnName
    ,因为您实际上有一些

现在,有一些方法可以绕过整个“第一列必须是布尔值”的问题,但坦率地说,这样做的代码要少得多

我还强烈建议您查看一下SwingWorker,并使用它来加载所有数据,否则您可能会发现,在开始加载数据时,UI会突然停止,这通常相当令人不快

看看


有关更多详细信息,请参见:
String getValueAt(…)
。这应该返回一个对象,而不是字符串,特别是,如果columnIndex为0,它应该返回一个
布尔值
,以符合您的
getColumnClass
和显示可编辑JCheckBox的需要。哦,它应该返回一个对象吗?我试图将数据数组的第0列赋值为false,但由于数据数组的类型为String,所以出现了一个错误。如果将数据数组设置为对象,我是否应该设置数据类型(我想我已经尝试过了,但遇到了错误..)。您需要查看API以了解更多信息。
getValueAt(…)
方法的签名是什么?API将告诉您。至于您的错误,您需要修复它们,但我100%确定第0列的数据必须是
布尔值
。谢谢大家的输入,非常感谢!这看起来不对:
String getValueAt(…)
。这应该返回一个对象,而不是字符串,特别是,如果columnIndex为0,它应该返回一个
布尔值
,以符合您的
getColumnClass
和显示可编辑JCheckBox的需要。哦,它应该返回一个对象吗?我试图将数据数组的第0列赋值为false,但由于数据数组的类型为String,所以出现了一个错误。如果将数据数组设置为对象,我是否应该设置数据类型(我想我已经尝试过了,但遇到了错误..)。您需要查看API以了解更多信息。
getValueAt(…)
方法的签名是什么?API将告诉您。至于您的错误,您需要修复它们,但我100%确定第0列的数据必须是
布尔值
。谢谢大家的输入,非常感谢!在
DataTableModel
类的
setValueAt()方法中
import java.awt.BorderLayout;
import java.awt.EventQueue;
import java.sql.SQLException;
import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.table.AbstractTableModel;

public class TestTableModel02 {

    public static void main(String[] args) {
        new TestTableModel02();
    }

    public TestTableModel02() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                }

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.setLayout(new BorderLayout());
                frame.add(new JScrollPane(new JTable(new DataTableModel())));
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class DataTableModel extends AbstractTableModel {

        private Object[][] data;
        private String[] header = {"", "KB Name", "fpGUID"};

        public DataTableModel() {//throws SQLException {
            // ========= CONNECTS TO DB AND PULLS RESULTS ==========

            // GETS RESULTS SET CALLED "rs"

            // populate data array
//            int counter = 0;
//            while (rs.next()) {
//                //data[counter][0] = "sfsdfsdfs ";
//                data[counter][1] = (String) rs.getObject(2);
//                data[counter][2] = (String) rs.getObject(4);
//
//                counter++;
//            }
            // =====================================================

            data = new Object[4][3];
            data[0] = new Object[]{false, "Help", "1234"};
            data[1] = new Object[]{false, "On fire", "5648"};
            data[2] = new Object[]{false, "Drowning", "9012"};
            data[3] = new Object[]{false, "Micky Mouse", "3456"};
        }

        @Override
        public Object getValueAt(int rowIndex, int columnIndex) {
            return data[rowIndex][columnIndex];
        }

        @Override
        public boolean isCellEditable(int row, int col) {
            return col == 0;
        }

        @Override
        public Class getColumnClass(int column) {
            if (column == 0) {
                return Boolean.class;
            } else {
                return String.class;
            }
        }

        @Override
        public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
            if (columnIndex == 0) {
                if (aValue instanceof Boolean) {
                    data[rowIndex][columnIndex] = (Boolean)aValue;
                    fireTableCellUpdated(rowIndex, columnIndex);
                }
            }
        }

        @Override
        public int getRowCount() {
            return data.length;
        }

        @Override
        public int getColumnCount() {
            return header.length;
        }

        @Override
        public String getColumnName(int column) {
            return header[column];
        }
    }
}