简体   繁体   English

JTable JComboBox默认在列表扩展时显示第一项

[英]JTable JComboBox is defaulting to display 1st item when list is expanded

I have been trying to determine why my JComboBox is displaying the 1st item in the list through numerous Google searches, but I'm struggling to find relevant help. 我一直在尝试确定为什么我的JComboBox通过大量Google搜索显示列表中的第一项,但是我一直在努力寻找相关的帮助。 It could be that I don't know the correct terminology (hence the overly specific title of this question) and thus not finding the information that would explain my issue. 可能是因为我不知道正确的术语(因此这个问题的标题太具体了),因此找不到可解释我问题的信息。 I checked out the JComboBox API, and few of the listeners and models that it uses, but they did not seem likely candidates. 我签出了JComboBox API,以及它使用的一些侦听器和模型,但是它们似乎不太可能成为候选对象。

The JComboBox in question is inside a JTable, so I am not aware if that changes the default behaviour of it. 有问题的JComboBox位于JTable内部,因此我不知道这是否会更改其默认行为。 The code I am using is as below: 我使用的代码如下:

//row and col are final due to usage inside anonymous inner class
public TableCellEditor getCellEditor(final int row, final int col)
{
    String[] listItems = new String[arrayList.getSize()];
    int i = -1;

    for(String s : arrayList)
    {
        i++;
        listItems[i] = s;
    }

    JComboBox<String> box = new JComboBox<>(listItems);
    box.addItemListener(new ItemListener()
    {
        public void itemStateChanged(ItemEvent e)
        {
            if(e.getStateChange() == ItemEvent.SELECTED)
            {
                if(e.getItem().equals("Add/Edit Projectile"))
                {
                    //Where Editor is a JFrame that will be opened 
                    new Editor();
                }
            }
        }
    });

    DefaultCellEditor list = new DefaultCellEditor(box);
}

Please note that the Arraylist in my program does not contain Strings, but instead a more complicated set of custom objects that I believe would distract from the main issue. 请注意,我程序中的Arraylist不包含字符串,而是一组更复杂的自定义对象,我相信这些对象会分散主要问题的注意力。

I haven't included a Renderer for JComboBox's in the JTable as I was happy enough with the way it appeared, and figured that my problem was more going to be something I have neglected to implement in the model/implemented wrong. 我没有在JTable中包含JComboBox的渲染器,因为我对它的显示方式非常满意,并发现我的问题更多是我在模型/实现错误中忽略了。

I've also provided a couple of screenshots to better portray my problem. 我还提供了一些屏幕截图,以更好地描述我的问题。 The first image is when the JComboBox is not selected, and simply displaying the currently selected item. 第一个图像是未选择JComboBox时,仅显示当前选择的项目。 未选中,默认状态

The second image is when I have just clicked the JComboBox to bring up the list. 第二张图片是当我单击JComboBox弹出列表时。 As depicted, it will immediately bring up that first item, no matter what it is. 如图所示,无论它是什么,它都会立即显示该第一项。 已选择,列表已展开

If anyone has any suggestions as to where to look/solutions, I would be very grateful. 如果有人对在哪里查找/解决方案有任何建议,我将不胜感激。


EDIT 编辑

My particular table has two columns, where the left column is a variable name, and the right column is the value associated with the variable. 我的特定表有两列,其中左列是变量名,右列是与变量关联的值。 The tables role is to display the properties of a selected object, where each value for different variable for different objects are likely to not be the same. 表的作用是显示所选对象的属性,其中不同对象的不同变量的每个值可能都不相同。

In this particular case, the cell displays a JComboBox with all the available Projectiles in the game we are making. 在这种情况下,该单元会显示一个JComboBox,其中包含我们正在制作的游戏中所有可用的投射物。 Each enemy has a different type of projectile it defaults to. 每个敌人都有默认的不同类型的弹丸。 So when I click on a different enemy in our game area, the table will display all of their current properties (defaults if they have not been changed). 因此,当我在游戏区域中单击其他敌人时,该表将显示其所有当前属性(如果尚未更改,则为默认属性)。

Enemies do have a getter for the Projectile, so I could determine what the currently selected enemy is, get it's projectile, do a toString() to find how it is to be represented in the list, and do a setValueAt(). 敌人的确有射弹的吸气剂,因此我可以确定当前选择的敌人是什么,使其成为射弹,并执行toString()以查找其在列表中的表示方式,然后执行setValueAt()。

The only problem is at the moment it is always selecting the first item in the list when the list is expanded. 唯一的问题是,当列表扩展时,它始终会选择列表中的第一项。

Unless the values for the JComboBox are dynamically generated for each row, you should be able to just prepare the CellEditor ahead of time, for example... 除非为每行动态生成JComboBox的值,否则您应该能够提前准备CellEditor ,例如...

JComboBox cb = new JComboBox(new String[]{"1", "2", "3", "4"});
DefaultCellEditor editor = new DefaultCellEditor(cb);

JTable table = new JTable(new DefaultTableModel(5, 1));
table.getColumnModel().getColumn(0).setCellEditor(editor);

This will set the selected value of the editor to the value of the cell when the editing process starts 当编辑过程开始时,这会将编辑器的选定值设置为单元格的值

在此处输入图片说明在此处输入图片说明

Updated 更新

In the case where the combobox values are dynamically generate per row, you could do something more like... 在每行动态生成组合框值的情况下,您可以执行更多类似的操作...

JComboBox cb = new JComboBox();
DefaultCellEditor editor = new DefaultCellEditor(cb) {

    @Override
    public Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column) {
        JComboBox editor = (JComboBox) getComponent();
        String[] listItems = new String[arrayList.getSize()];
        int i = -1;
        for (String s : arrayList) {
            i++;
            listItems[i] = s;
        }

        DefaultComboBoxModel model = new DefaultComboBoxModel(listItems);
        editor.setModel(model);
        editor.setSelectedItem(value);
        return editor;
    }
};

JTable table = new JTable(new DefaultTableModel(5, 1));
table.getColumnModel().getColumn(0).setCellEditor(editor);

Note the use of editor.setSelectedItem(value); 注意使用editor.setSelectedItem(value); , this will set the selected value to the cells current value... ,这会将所选值设置为单元格的当前值...

You could also re-use the model, clearing it each time and re-filling it with new values. 您还可以重新使用模型,每次都将其清除,并用新值重新填充它。 You might find this more efficient if you have a large number of rows as you won't need to constantly create a new model each time a cell is edited 如果行数很多,您可能会发现这种方法更有效,因为每次编辑单元格时都不需要不断创建新模型

Thow this is an oldie... 这是老歌...

Your problem is most likely you don't implement "equals" in the class used in the combo. 您的问题很可能是您没有在组合中使用的类中实现“等于”。

The Combo needs to select the current item when it is being prepared and does so by iterating through the elements of the model and selects the first one that is equal to the value in the cell. 组合需要在准备当前项目时选择它,方法是遍历模型的各个元素并选择与单元格中的值相等的第一个项目。 If none is encountered then it leaves the combo as is (either first element or the last used element in a previous cell edit) 如果没有遇到任何问题,则它将组合保持不变(上一个单元格编辑中的第一个元素或最后一个使用的元素)

This is how you should default to the previously selected element: 这是默认应使用先前选择的元素的方式:

//...
Object selectedItem = box.getSelectedItem();
//Add some elements to the jComboBox
box.setSelectedItem(selectedItem);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM