简体   繁体   English

在Jtable中添加JCombobox并在Swing java中获取该行和列

[英]Adding JCombobox in Jtable and Getting that Row and Column in Swing java

I have One Jtable in which i have added JComobox like this. 我有一个Jtable,我在其中添加了JComobox。

TableColumn sportColumn = jTable1.getColumnModel().getColumn(2);
        comboBox = new JComboBox();
        comboBox.addItem("Snowboarding");
        comboBox.addItem("Rowing");
        comboBox.addItem("Chasing toddlers");
        comboBox.addItem("Speed reading");
        comboBox.addItem("Teaching high school");
        comboBox.addItem("None");
        sportColumn.setCellEditor(new DefaultCellEditor(comboBox));

and i have added one mouse event of jtable like this. 我添加了一个像这样的jtable鼠标事件。

private void jTable1MouseClicked(java.awt.event.MouseEvent evt) {                                     
        // TODO add your handling code here:
        try {
            int row = jTable1.rowAtPoint(evt.getPoint());
            int col = jTable1.columnAtPoint(evt.getPoint());

            System.out.println("Row" + row + "Column" + col);

        } catch (Exception e) {
            e.printStackTrace();
        }

    }

and i am getting proper out put of row and column. 我正在把行和列放到正确的位置。 在此输入图像描述

but when i click on the cell where i added Jcombobox that time its not giving out put of that row and column. 但当我点击我添加Jcombobox的单元格时,它没有给出该行和列的放置。 still i have called clickevent of table in combobox click event but its giving all time row 0 and even column 0 here screen shot. 仍然我在组合框点击事件中调用了表格的clickevent但是它给了所有时间第0行甚至第0列这里的屏幕截图。

在此输入图像描述

so how do i solved it so i can have that row and column? 所以我怎么解决它所以我可以有那个行和列?

As I see it, you have three basic options... 在我看来,你有三个基本选择......

You Could... 你可以...

Attach a CellEditorListener to the DefaultCellEditor and monitor for editingStopped events... CellEditorListener附加到DefaultCellEditor并监视editingStopped事件...

editor.addCellEditorListener(new CellEditorListener() {
    @Override
    public void editingStopped(ChangeEvent e) {
        System.out.println("Editing stopped");
        TableCellEditor editor = (TableCellEditor) e.getSource();
        Object value = editor.getCellEditorValue();
        System.out.println("Selected value = " + value);
    }

    @Override
    public void editingCanceled(ChangeEvent e) {
    }
});

The problem with this, is it's not possible to actually determine the cell that's been edited. 这个问题是,实际上无法确定已编辑的单元格。 Even with a reference to the JTable , by the time you receive this event, the table is no longer in edit mode...So all you know is the value of the editor... 即使引用了JTable ,当你收到这个事件时,表也不再处于编辑模式......所以你所知道的就是编辑器的价值......

You Could... 你可以...

Attach a TableModelListener to the TableModel ... TableModelListener附加到TableModel ...

model.addTableModelListener(new TableModelListener() {
    @Override
    public void tableChanged(TableModelEvent e) {
        int type = e.getType();
        switch (type) {
            case TableModelEvent.UPDATE:
                if (e.getFirstRow() - e.getLastRow() == 0) {
                    TableModel model = (TableModel) e.getSource();
                    int row = e.getFirstRow();
                    int col = e.getColumn();
                    System.out.println("Update " + row + "x" + col + " = " + model.getValueAt(row, col));
                }
                break;
        }
    }
});

This will let you know when the value of a cell has changed (and a lot of other things, but this is what we're interested), what it won't tell you, is why it changed. 这会告诉你什么时候一个单元格的价值发生了变化(还有很多其他的东西,但这就是我们感兴趣的东西),它不会告诉你什么,这就是它改变的原因。

This approach is good, because it provides all the information you need to know in order to find the value and the cell. 这种方法很好,因为它提供了您需要知道的所有信息,以便找到值和单元格。

You Could... 你可以...

Simply override the TableModel 's setValueAt method and provide some sort of notification of your own... 只需覆盖TableModelsetValueAt方法,并提供自己的某种通知......

While this is kind of duplicating the functionality of the TableModelListener you could devise the event information so that it provides more relevant information as the TableModelEvent covers a lot of user cases... 虽然这有点复制了TableModelListener的功能,但您可以设计事件信息,以便它提供更多相关信息,因为TableModelEvent涵盖了很多用户案例......

Example

Below is an example taken TableRenderDemo and modified to to demonstrate the first two concepts 下面是一个采用TableRenderDemo的示例,并进行了修改以演示前两个概念

import java.awt.BorderLayout;
import javax.swing.DefaultCellEditor;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.table.AbstractTableModel;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.TableCellRenderer;
import javax.swing.table.TableColumn;
import java.awt.Component;
import java.awt.Dimension;
import javax.swing.event.CellEditorListener;
import javax.swing.event.ChangeEvent;
import javax.swing.event.TableModelEvent;
import javax.swing.event.TableModelListener;
import javax.swing.table.TableCellEditor;
import javax.swing.table.TableModel;

/**
 * TableRenderDemo is just like TableDemo, except that it explicitly initializes
 * column sizes and it uses a combo box as an editor for the Sport column.
 */
public class TableRenderDemo extends JPanel {

    public TableRenderDemo() {
        super(new BorderLayout());

        JTable table = new JTable(new MyTableModel());
        table.setPreferredScrollableViewportSize(new Dimension(500, 70));
        table.setFillsViewportHeight(true);

        //Create the scroll pane and add the table to it.
        JScrollPane scrollPane = new JScrollPane(table);

        //Set up column sizes.
        initColumnSizes(table);

        //Fiddle with the Sport column's cell editors/renderers.
        setUpSportColumn(table, table.getColumnModel().getColumn(2));

        //Add the scroll pane to this panel.
        add(scrollPane);
    }

    /*
     * This method picks good column sizes.
     * If all column heads are wider than the column's cells'
     * contents, then you can just use column.sizeWidthToFit().
     */
    private void initColumnSizes(JTable table) {
        MyTableModel model = (MyTableModel) table.getModel();
        model.addTableModelListener(new TableModelListener() {
            @Override
            public void tableChanged(TableModelEvent e) {
                int type = e.getType();
                switch (type) {
                    case TableModelEvent.UPDATE:
                        if (e.getFirstRow() - e.getLastRow() == 0) {
                            TableModel model = (TableModel) e.getSource();
                            int row = e.getFirstRow();
                            int col = e.getColumn();
                            System.out.println("Update " + row + "x" + col + " = " + model.getValueAt(row, col));
                        }
                        break;
                }
            }
        });
        TableColumn column = null;
        Component comp = null;
        int headerWidth = 0;
        int cellWidth = 0;
        Object[] longValues = model.longValues;
        TableCellRenderer headerRenderer
                        = table.getTableHeader().getDefaultRenderer();

        for (int i = 0; i < 5; i++) {
            column = table.getColumnModel().getColumn(i);

            comp = headerRenderer.getTableCellRendererComponent(
                            null, column.getHeaderValue(),
                            false, false, 0, 0);
            headerWidth = comp.getPreferredSize().width;

            comp = table.getDefaultRenderer(model.getColumnClass(i)).
                            getTableCellRendererComponent(
                                            table, longValues[i],
                                            false, false, 0, i);
            cellWidth = comp.getPreferredSize().width;

            column.setPreferredWidth(Math.max(headerWidth, cellWidth));
        }
    }

    public void setUpSportColumn(final JTable table,
                    TableColumn sportColumn) {
        //Set up the editor for the sport cells.
        JComboBox comboBox = new JComboBox();
        comboBox.addItem("Snowboarding");
        comboBox.addItem("Rowing");
        comboBox.addItem("Knitting");
        comboBox.addItem("Speed reading");
        comboBox.addItem("Pool");
        comboBox.addItem("None of the above");
        TableCellEditor editor = new DefaultCellEditor(comboBox);
        editor.addCellEditorListener(new CellEditorListener() {

            @Override
            public void editingStopped(ChangeEvent e) {
                System.out.println("Editing stopped");
                TableCellEditor editor = (TableCellEditor) e.getSource();
                Object value = editor.getCellEditorValue();
                System.out.println("Selected value = " + value);
            }

            @Override
            public void editingCanceled(ChangeEvent e) {
            }
        });
        sportColumn.setCellEditor(editor);

        //Set up tool tips for the sport cells.
        DefaultTableCellRenderer renderer
                        = new DefaultTableCellRenderer();
        renderer.setToolTipText("Click for combo box");
        sportColumn.setCellRenderer(renderer);
    }

    class MyTableModel extends AbstractTableModel {

        private String[] columnNames = {"First Name",
            "Last Name",
            "Sport",
            "# of Years",
            "Vegetarian"};
        private Object[][] data = {
            {"Kathy", "Smith",
                "Snowboarding", new Integer(5), new Boolean(false)},
            {"John", "Doe",
                "Rowing", new Integer(3), new Boolean(true)},
            {"Sue", "Black",
                "Knitting", new Integer(2), new Boolean(false)},
            {"Jane", "White",
                "Speed reading", new Integer(20), new Boolean(true)},
            {"Joe", "Brown",
                "Pool", new Integer(10), new Boolean(false)}
        };

        public final Object[] longValues = {"Jane", "Kathy",
            "None of the above",
            new Integer(20), Boolean.TRUE};

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

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

        @Override
        public String getColumnName(int col) {
            return columnNames[col];
        }

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

        /*
         * JTable uses this method to determine the default renderer/
         * editor for each cell.  If we didn't implement this method,
         * then the last column would contain text ("true"/"false"),
         * rather than a check box.
         */
        @Override
        public Class getColumnClass(int c) {
            return getValueAt(0, c).getClass();
        }

        /*
         * Don't need to implement this method unless your table's
         * editable.
         */
        @Override
        public boolean isCellEditable(int row, int col) {
            //Note that the data/cell address is constant,
            //no matter where the cell appears onscreen.
            if (col < 2) {
                return false;
            } else {
                return true;
            }
        }

        /*
         * Don't need to implement this method unless your table's
         * data can change.
         */
        @Override
        public void setValueAt(Object value, int row, int col) {
            data[row][col] = value;
            fireTableCellUpdated(row, col);
        }
    }

    /**
     * Create the GUI and show it. For thread safety, this method should be
     * invoked from the event-dispatching thread.
     */
    private static void createAndShowGUI() {
        //Create and set up the window.
        JFrame frame = new JFrame("TableRenderDemo");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        //Create and set up the content pane.
        TableRenderDemo newContentPane = new TableRenderDemo();
        newContentPane.setOpaque(true); //content panes must be opaque
        frame.setContentPane(newContentPane);

        //Display the window.
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        //Schedule a job for the event-dispatching thread:
        //creating and showing this application's GUI.
        javax.swing.SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                createAndShowGUI();
            }
        });
    }
}

Using below code you can get values of selected rows and column. 使用下面的代码,您可以获得所选行和列的值。 在此输入图像描述

table.addMouseListener(new MouseAdapter() 
      {
        @Override
        public void mouseClicked(MouseEvent e) 
        {
            try {
                int rowss = table.rowAtPoint(e.getPoint());
                System.out.println("rowss" + rowss);
                printDebugData(table);
            } catch (ParseException ex) {
                Logger.getLogger(ShowEmployee.class.getName()).log(Level.SEVERE, null, ex);
            }
        }

        private void printDebugData(JTable jTable1) throws ParseException
        {
              String selectedData = null;

            int numRows = jTable1.getRowCount();
            int numCols = jTable1.getColumnCount();
            int[] selectedRow = jTable1.getSelectedRows();
            int[] selectedColumns = jTable1.getSelectedColumns();
            javax.swing.table.TableModel model = jTable1.getModel();
            for (int i = 0; i < selectedRow.length; i++)
            {
                for (int j = 0; j < selectedColumns.length; j++) 
                {
                    selectedData = (String) jTable1.getValueAt(selectedRow[i], selectedColumns[j]);
                }
                System.out.println("Selected: " + selectedData);
            }
        }
        });

  }

check with mouselistner with your jtbale. 用你的jtbale检查mouselistner。

UPDATE : add this two line before printdebugdata() called. 更新:在printdebugdata()调用之前添加这两行。

  int rowss = table.rowAtPoint(e.getPoint());
  System.out.println("rowss" + rowss);

I got the row number check my output. 我得到行号检查我的输出。

OUTPUT : 输出:

rowss0
Selected: Smith
rowss0
Selected: Smith
rowss1
Selected: Snowboarding
rowss1
Selected: Rowing
rowss1
Selected: Rowing
rowss1
Selected: Rowing
rowss2
Selected: Snowboarding
rowss2
Selected: Snowboarding
rowss2
Selected: Snowboarding
rowss2
Selected: Snowboarding

Thanks.. 谢谢..

Well Its Little But strange for me but ya i do solved it but i dont think so that is the proper ansewer but i solved it. 好吧它的小但对我来说很奇怪,但是我确实解决了它,但我不认为这是正确的ansewer但我解决了它。 i called. 我打了电话。 Combo button Action Performed event and have called Mouse click of jtable in that. 组合按钮操作执行事件,并在其中调用鼠标单击jtable。 with null instead of the Event. 用null而不是Event。 check it out. 看看这个。

 comboBox.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                //throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
                jTable1MouseClicked(null);
            }
        });


 private void jTable1MouseClicked(java.awt.event.MouseEvent evt) {                                     
        // TODO add your handling code here:
        try {
            //evt.getPoint();
            System.out.println("row" + jTable1.getSelectedRow());
            System.out.println("col" + jTable1.getSelectedColumn());
        } catch (Exception e) {
            e.printStackTrace();
        }

    }                                    

may be its not Right way but i solved it this threw. 可能是它不正确的方式,但我解决了它扔了。 its working. 它的工作。

best solution is 最佳解决方案是

jTable1.getModel().addTableModelListener(new TableModelListener() {

            @Override
            public void tableChanged(TableModelEvent e) {
                System.out.println("Changed Column"+e.getColumn());
                System.out.println("first row"+e.getFirstRow());
            }
        });

    }

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

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