1

i have a JTable and I'm adding three JComboBoxes to three different columns. Now i want to set the selected item for every row i have. The problem is, i need the ID of every row to do that. So i tried different Listeners and the best result came with a FocusListener, but then i always have to click at the row first and then at the JComboBox and this is laborious. Here is an example:

JTable table = new JTable();
    Vector<ArrayList<Object>> data = new Vector<ArrayList<Object>>();
    for (int i = 0; i < 5; i++)
    {
        ArrayList<Object> object = new ArrayList<Object>();
        object.add(i);
        object.add("name");
        object.add(i+1);
        object.add(i+1);
        object.add(i+1);
        data.add(object);
    }
    DefaultTableModel tableModel = new DefaultTableModel() {
        /**
         * 
         */
        private static final long serialVersionUID = 1L;

        @Override
        public boolean isCellEditable(int row, int column) {
            if (column < 2)
                return false;
            return true;
        }
    };
    tableModel.setColumnIdentifiers(new String[] {"ID", "Name", "OK", "Other", "Error"});
    tableModel.addTableModelListener(new TableModelListener()
    {

        @Override
        public void tableChanged(TableModelEvent e)
        {
            if (e.getType() == TableModelEvent.UPDATE)
            {
                int row = e.getFirstRow();
                int column = e.getColumn();
                TableModel table_model = (TableModel) e.getSource();
                ArrayList<Object> changed_data = (ArrayList<Object>) table_model.getValueAt(row, column);
                String row_id = String.valueOf(table_model.getValueAt(row, 0));
                for (ArrayList<Object> list : data)
                {
                    String compare_id = String.valueOf(list.get(0));
                    if (row_id.equals(compare_id))
                    {
                        list.set(column, String.valueOf(changed_data.get(0)));
                        for (int i = table_model.getRowCount()-1; i >= 0 ; i--)
                        {
                            tableModel.removeRow(i);
                        }

                        for (ArrayList<Object> object : data)
                        {
                            Vector<String> vector = new Vector<String>();
                            vector.addElement(String.valueOf(object.get(0)));
                            vector.addElement(String.valueOf(object.get(1)));
                            vector.addElement(String.valueOf(object.get(2)));
                            vector.addElement(String.valueOf(object.get(3)));
                            vector.addElement(String.valueOf(object.get(4)));
                            tableModel.addRow(vector);
                        }

                        TableColumn column_ok = table.getColumnModel().getColumn(2);
                        TableColumn column_other = table.getColumnModel().getColumn(3);
                        TableColumn column_error = table.getColumnModel().getColumn(4);

                        JComboBox<ArrayList<Object>> combobox_ok = new JComboBox<ArrayList<Object>>(data);
                        JComboBox<ArrayList<Object>> combobox_other = new JComboBox<ArrayList<Object>>(data);
                        JComboBox<ArrayList<Object>> combobox_error = new JComboBox<ArrayList<Object>>(data);

                        column_ok.setCellEditor(new DefaultCellEditor(combobox_ok));
                        column_other.setCellEditor(new DefaultCellEditor(combobox_other));
                        column_error.setCellEditor(new DefaultCellEditor(combobox_error));
                        break;
                    }
                }
            }
        }
    });
    table.setModel(tableModel);
    for (ArrayList<Object> object : data)
    {
        Vector<String> vector = new Vector<String>();
        vector.addElement(String.valueOf(object.get(0)));
        vector.addElement(String.valueOf(object.get(1)));
        vector.addElement(String.valueOf(object.get(2)));
        vector.addElement(String.valueOf(object.get(3)));
        vector.addElement(String.valueOf(object.get(4)));
        tableModel.addRow(vector);
    }

    TableColumn column_ok = table.getColumnModel().getColumn(2);
    TableColumn column_other = table.getColumnModel().getColumn(3);
    TableColumn column_error = table.getColumnModel().getColumn(4);

    JComboBox<ArrayList<Object>> combobox_ok = new JComboBox<ArrayList<Object>>(data);
    JComboBox<ArrayList<Object>> combobox_other = new JComboBox<ArrayList<Object>>(data);
    JComboBox<ArrayList<Object>> combobox_error = new JComboBox<ArrayList<Object>>(data);

    column_ok.setCellEditor(new DefaultCellEditor(combobox_ok));
    column_other.setCellEditor(new DefaultCellEditor(combobox_other));
    column_error.setCellEditor(new DefaultCellEditor(combobox_error));

    JScrollPane scrollPane = new JScrollPane();
    scrollPane.getViewport().add(table);

    JFrame frame = new JFrame();
    frame.add(scrollPane);
    frame.setSize(400, 200);
    frame.setVisible(true);

Now, in the first row, third column ("OK"), you can choose in the JComboBox different entries which represent a row. So a row has three JComboBoxes which reference to another row. If you click in such a JComboBox, you will notice it always chooses the first entry and not the entry with the number you saw before clicking at it.

Maybe now you understand what i want to do?

mavok
  • 27
  • 14
  • 1
    For better help sooner, post a [MCVE] or [Short, Self Contained, Correct Example](http://www.sscce.org/). – Andrew Thompson Oct 12 '16 at 08:23
  • Please, explain as best as possible what, where and how is going wrong and what would be the desired effect. I can't understund your question in this form. – Krzysztof Cichocki Oct 12 '16 at 08:40
  • I will update the question when i have coded an example. – mavok Oct 12 '16 at 08:51
  • Like [this](http://stackoverflow.com/a/7356518/230513)? – trashgod Oct 12 '16 at 09:17
  • @trashgod i don't think this is the solution. I don't want to change the value. I just want to click in the JComboBox and the selected item should be the item with the value before I clicked in the JComboBox. For example, if you run the code above, in the first row the value in column "OK" ist 1. So if you click in the JCombobox the item with the 1 as the first value should be selected. – mavok Oct 12 '16 at 09:40

1 Answers1

2

If you click in such a JComboBox, you will notice it always chooses the first entry and not the entry with the number you saw before clicking at it.

Focusing on this aspect of the problem, the following simplified, complete example always displays the selected entry when the cell's editor is active. You can replace the combo's default renderer to display a different result as needed. In addition,

  • Override getPreferredScrollableViewportSize() to establish the desired size of the table.

  • Use type parameters where possible; override getColumnClass() as needed, for example.

  • Override getValueAt(), as shown here and here, for dependent data.

  • Note the simplified implementation of isCellEditable() below.

image

import java.awt.Dimension;
import java.awt.EventQueue;
import java.util.Arrays;
import java.util.Vector;
import javax.swing.DefaultCellEditor;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumn;

/**
 * @see https://stackoverflow.com/q/39993746/230513
 */
public class TableComboTest {

    private Vector<Vector<String>> createData() {
        Vector<Vector<String>> data = new Vector<Vector<String>>();
        for (int i = 0; i < 5; i++) {
            Vector<String> rowVector = new Vector<String>();
            rowVector.add(String.valueOf(i));
            rowVector.add("name");
            rowVector.add(String.valueOf(i + 1));
            rowVector.add(String.valueOf(i + 1));
            rowVector.add(String.valueOf(i + 1));
            data.add(rowVector);
        }
        return data;
    }

    private void display() {
        Vector<Vector<String>> data = createData();
        Vector<String> names = new Vector<>(Arrays.asList("ID", "Name", "OK", "Other", "Error"));
        DefaultTableModel tableModel = new DefaultTableModel(data, names) {

            @Override
            public boolean isCellEditable(int row, int column) {
                return column > 1;
            }
        };
        JTable table = new JTable(tableModel) {
            @Override
            public Dimension getPreferredScrollableViewportSize() {
                return new Dimension(getPreferredSize().width, getRowHeight() * 4);
            }
        };

        TableColumn column_ok = table.getColumnModel().getColumn(2);
        TableColumn column_other = table.getColumnModel().getColumn(3);
        TableColumn column_error = table.getColumnModel().getColumn(4);

        String[] choices = new String[]{"1", "2", "3", "4", "5"};
        JComboBox<String> combobox_ok = new JComboBox<>(choices);
        JComboBox<String> combobox_other = new JComboBox<String>(choices);
        JComboBox<String> combobox_error = new JComboBox<String>(choices);

        column_ok.setCellEditor(new DefaultCellEditor(combobox_ok));
        column_other.setCellEditor(new DefaultCellEditor(combobox_other));
        column_error.setCellEditor(new DefaultCellEditor(combobox_error));

        JFrame frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(new JScrollPane(table));
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new TableComboTest()::display);
    }
}
Community
  • 1
  • 1
trashgod
  • 203,806
  • 29
  • 246
  • 1,045