具有多个字段的 Java JTable 对象

发布于 2024-08-16 14:26:47 字数 226 浏览 4 评论 0原文

我有一个具有 X 个字段的对象。 JTable 中的每一行对应一个项目。行中的每一列代表该项目的一个字段。我还需要维护对该项目的引用(该项目也有一个唯一的 ID 字段),以便我可以确定所选单元格中的项目。

首选方法是将实际对象放入表中的每个单元格中,并使用各种渲染器来显示项目,还是简单地将字段值放入每个单元格中,并有一个隐藏列,其中包含我可以使用的项目 ID当我需要知道商品 ID 时参考?

谢谢, 杰夫

I have an object that has X number of fields. Each row in my JTable corresponds to one item. Each column in the row represents a field for that item. I also need to maintain a reference to the item (the item has a unique ID field as well) so I can determine the item in the selected cell.

Would the preferred approach to this be putting the actual object in each cell in the table and using various renderers to display the item or to simply put the field values in each of the cells and have a hidden column that has the item ID that I can reference when I need to know the item ID?

thanks,
Jeff

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

我爱人 2024-08-23 14:26:47

我会编写一个自定义表模型(而不是尝试将您的设计硬塞到默认表模型实现中)。然后,该模型保存您的实际对象,并在其方法实现(例如 getValueAt)中,它将每个字段视为一列。


简单的例子(未经测试,但应该很好地说明这个想法):

import java.util.List;
import java.util.ArrayList;
import javax.swing.table.AbstractTableModel;

/**
 * Simple table model for displaying properties common to all objects.
 * Note that all methods must run inside the event dispatch thread.
 */
public class ObjectPropertyTableModel extends AbstractTableModel {
    private final List<Object> objects = new ArrayList<Object>();

    public void addObject(Object obj) {
        addObject(obj, objects.size());
    }

    public void addObject(Object obj, int index) {
        objects.add(index, obj);
        fireTableRowsInserted(index, index);
    }

    public void removeObject(Object obj) {
        int index = objects.indexOf(obj);
        objects.remove(index);
        fireTableRowsDeleted(index, index);
    }

    public Object getObject(int rowIndex) {
        return objects.get(rowIndex);
    }

    @Override
    public int getRowCount() {
        return objects.size();
    }

    @Override
    public int getColumnCount() {
        return 3;
    }

    @Override
    public String getColumnName(int columnIndex) {
        switch (columnIndex) {
        case 0: return "toString";
        case 1: return "hashCode";
        case 2: return "class";
        default: throw new IndexOutOfBoundsException();
        }
    }

    @Override
    public Class<?> getColumnClass(int columnIndex) {
        switch (columnIndex) {
        case 0: return String.class;
        case 1: return Integer.class;
        case 2: return Class.class;
        default: throw new IndexOutOfBoundsException();
        }
    }

    @Override
    public Object getValueAt(int rowIndex, int columnIndex) {
        Object obj = objects.get(rowIndex);
        switch (columnIndex) {
        case 0: return obj.toString();
        case 1: return obj.hashCode();
        case 2: return obj.getClass();
        default: throw new IndexOutOfBoundsException();
        }
    }
}

I'd write a custom table model (as opposed to trying to shoehorn your design into the default table model implementation). This model then holds your actual objects, and in its method implementations (such as getValueAt), it'd consider each of the fields as a column.


Simple example (not tested, but should illustrate the idea nicely):

import java.util.List;
import java.util.ArrayList;
import javax.swing.table.AbstractTableModel;

/**
 * Simple table model for displaying properties common to all objects.
 * Note that all methods must run inside the event dispatch thread.
 */
public class ObjectPropertyTableModel extends AbstractTableModel {
    private final List<Object> objects = new ArrayList<Object>();

    public void addObject(Object obj) {
        addObject(obj, objects.size());
    }

    public void addObject(Object obj, int index) {
        objects.add(index, obj);
        fireTableRowsInserted(index, index);
    }

    public void removeObject(Object obj) {
        int index = objects.indexOf(obj);
        objects.remove(index);
        fireTableRowsDeleted(index, index);
    }

    public Object getObject(int rowIndex) {
        return objects.get(rowIndex);
    }

    @Override
    public int getRowCount() {
        return objects.size();
    }

    @Override
    public int getColumnCount() {
        return 3;
    }

    @Override
    public String getColumnName(int columnIndex) {
        switch (columnIndex) {
        case 0: return "toString";
        case 1: return "hashCode";
        case 2: return "class";
        default: throw new IndexOutOfBoundsException();
        }
    }

    @Override
    public Class<?> getColumnClass(int columnIndex) {
        switch (columnIndex) {
        case 0: return String.class;
        case 1: return Integer.class;
        case 2: return Class.class;
        default: throw new IndexOutOfBoundsException();
        }
    }

    @Override
    public Object getValueAt(int rowIndex, int columnIndex) {
        Object obj = objects.get(rowIndex);
        switch (columnIndex) {
        case 0: return obj.toString();
        case 1: return obj.hashCode();
        case 2: return obj.getClass();
        default: throw new IndexOutOfBoundsException();
        }
    }
}
白日梦 2024-08-23 14:26:47

您也许可以使用 Bean 表模型。如果没有,那么 JButtonTableModel 示例将向您展示如何实现 getValueAt/setValueAt() 方法并利用 RowTableModel 提供的功能,这样您就无需从头开始创建 TableModel。

You might be able to use the Bean Table Model. If not, then the JButtonTableModel examples shows how you might implement the getValueAt/setValueAt() methods and take advantage of the functionality provided by the RowTableModel so you don't need to create the TableModel from scratch.

樱娆 2024-08-23 14:26:47

我的首选方法是使用一个表模型,该模型从每列的字段返回一个值。为了能够获取对象的引用,我向模型添加了一个名为 getObjectFromRow 的方法,顾名思义,它返回与行索引对应的对象。这样您就可以在单元格中获得实际显示的数据,并且不需要隐藏列来获取对行对象的引用。当然,这需要自定义表格模型,但我认为这是值得的。
当然,使用渲染器来显示来自正确字段的数据也是可能的,但根据我的经验,这有几个问题,包括为不同数据类型编写所有渲染器的麻烦以及复制和复制的事实。表格中的粘贴开箱后无法正常工作。

My preferred approach is to have a table model which returns a value from the field for each column. To be able to get a reference to the object, I add a method to the model which could be called getObjectFromRow and as its name suggests, it returns the object corresponding to the row index. This way you can have the actual displayed data in the cell and you don't need a hidden column to get a reference to the row object. Of course this requires a custom table model but I think it's well worth the trouble.
Of course using renderers for displaying data from the correct field is also possible, but in my experience this has several problems, including the trouble of writing all the renderers for different data types and also the fact that copy & paste from the table does not work properly out of the box.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文