JTable celleditor可以支持同一列不同行的cell里面动态的组件

来源:互联网 发布:杀马特遇见洗剪吹 知乎 编辑:程序博客网 时间:2024/05/22 08:49
DefaultCellEditor封装了很多常用的editor组件,比如JTextField,JCheckBox,JComboBox,但是有时需要这样的情形:有些行需要JTextField,有些行需要JComboBox,这样就不能直接使用DefaultCellEditor了,其实实现起来也很简单,只要自己参照DefaultCellEditor实现一个自定义的CellEditor就可以了,

源代码如下:

import java.awt.Component;import java.awt.event.ActionEvent;import java.awt.event.ActionListener;import java.awt.event.FocusEvent;import java.awt.event.ItemEvent;import java.awt.event.ItemListener;import java.awt.event.MouseEvent;import java.io.Serializable;import java.util.EventObject;import java.util.List;import javax.swing.AbstractCellEditor;import javax.swing.JComboBox;import javax.swing.JComponent;import javax.swing.JLabel;import javax.swing.JTable;import javax.swing.JTextField;import javax.swing.event.DocumentEvent;import javax.swing.event.DocumentListener;import javax.swing.table.TableCellEditor;public class ConditionValueEditor extends AbstractCellEditor implementsTableCellEditor {//// Instance Variables///** The Swing component being edited. */protected JComponent editorComponent;/** * The delegate class which handles all methods sent from the * <code>CellEditor</code>. */protected EditorDelegate delegate;/** * An integer specifying the number of clicks needed to start editing. Even * if <code>clickCountToStart</code> is defined as zero, it will not * initiate until a click occurs. */protected int clickCountToStart = 1;private ConditionInfo info;public ConditionValueEditor(){}/** * Specifies the number of clicks needed to start editing. *  * @param count *            an int specifying the number of clicks needed to start editing * @see #getClickCountToStart */public void setClickCountToStart(int count) {clickCountToStart = count;}/** * Returns the number of clicks needed to start editing. *  * @return the number of clicks needed to start editing */public int getClickCountToStart() {return clickCountToStart;}//// Override the implementations of the superclass, forwarding all methods// from the CellEditor interface to our delegate.///** * Forwards the message from the <code>CellEditor</code> to the * <code>delegate</code>. *  * @see EditorDelegate#getCellEditorValue */public Object getCellEditorValue() {return delegate.getCellEditorValue();}/** * Forwards the message from the <code>CellEditor</code> to the * <code>delegate</code>. *  * @see EditorDelegate#isCellEditable(EventObject) */public boolean isCellEditable(EventObject anEvent) {//return delegate.isCellEditable(anEvent);return true;}/** * Forwards the message from the <code>CellEditor</code> to the * <code>delegate</code>. *  * @see EditorDelegate#shouldSelectCell(EventObject) */public boolean shouldSelectCell(EventObject anEvent) {return delegate.shouldSelectCell(anEvent);}/** * Forwards the message from the <code>CellEditor</code> to the * <code>delegate</code>. *  * @see EditorDelegate#stopCellEditing */public boolean stopCellEditing() {return delegate.stopCellEditing();}/** * Forwards the message from the <code>CellEditor</code> to the * <code>delegate</code>. *  * @see EditorDelegate#cancelCellEditing */public void cancelCellEditing() {delegate.cancelCellEditing();}@Overridepublic Component getTableCellEditorComponent(JTable table, Object value,boolean isSelected, int row, int column) {if (column == 1) {if (ConditionTableModel.class.isInstance(table.getModel())) {ConditionTableModel model = (ConditionTableModel) table.getModel();info = model.getRow(row);String paramName = info.getVariableName();String paramvalue = info.getValue();if (isEnumAttribute(paramName,info.getConditionCheckType())) {final JComboBox comboBox = new JComboBox();List<String> displayList = ... ...;String displayValue = ... ...;for(String text:displayList){comboBox.addItem(text);if(text.equals(displayValue)){comboBox.setSelectedItem(text);}}editorComponent = comboBox;comboBox.putClientProperty("JComboBox.isTableCellEditor",Boolean.TRUE);delegate = new EditorDelegate() {public void setValue(Object value) {comboBox.setSelectedItem(value);}public Object getCellEditorValue() {return comboBox.getSelectedItem();}public boolean shouldSelectCell(EventObject anEvent) {if (anEvent instanceof MouseEvent) {MouseEvent e = (MouseEvent) anEvent;return e.getID() != MouseEvent.MOUSE_DRAGGED;}return true;}public boolean stopCellEditing() {if (comboBox.isEditable()) {// Commit edited value.comboBox.actionPerformed(new ActionEvent(ConditionValueEditor.this, 0, ""));}return super.stopCellEditing();}};comboBox.addActionListener(delegate);} else {final JTextField textField = new JTextField(paramvalue);editorComponent = textField;this.clickCountToStart = 2;delegate = new EditorDelegate() {public void setValue(Object value) {textField.setText((value != null) ? value.toString() : "");}public Object getCellEditorValue() {return textField.getText();}};textField.addFocusListener(new   java.awt.event.FocusAdapter()   {                     public   void   focusLost(FocusEvent   e)   {                     info.setValue(textField.getText());                    }               });   textField.addActionListener(delegate);}if (!info.isParamCondition()) {editorComponent.setEnabled(false);}return editorComponent;}}JLabel label = new JLabel();label.setText((String) value);return label;}//// Protected EditorDelegate class///** * The protected <code>EditorDelegate</code> class. */protected class EditorDelegate implements ActionListener, ItemListener,Serializable {/** The value of this cell. */protected Object value;/** * Returns the value of this cell. *  * @return the value of this cell */public Object getCellEditorValue() {return value;}/** * Sets the value of this cell. *  * @param value *            the new value of this cell */public void setValue(Object value) {this.value = value;}/** * Returns true if <code>anEvent</code> is <b>not</b> a * <code>MouseEvent</code>. Otherwise, it returns true if the necessary * number of clicks have occurred, and returns false otherwise. *  * @param anEvent *            the event * @return true if cell is ready for editing, false otherwise * @see #setClickCountToStart * @see #shouldSelectCell */public boolean isCellEditable(EventObject anEvent) {if (anEvent instanceof MouseEvent) {return ((MouseEvent) anEvent).getClickCount() >= clickCountToStart;}return true;}/** * Returns true to indicate that the editing cell may be selected. *  * @param anEvent *            the event * @return true * @see #isCellEditable */public boolean shouldSelectCell(EventObject anEvent) {return true;}/** * Returns true to indicate that editing has begun. *  * @param anEvent *            the event */public boolean startCellEditing(EventObject anEvent) {return true;}/** * Stops editing and returns true to indicate that editing has stopped. * This method calls <code>fireEditingStopped</code>. *  * @return true */public boolean stopCellEditing() {fireEditingStopped();return true;}/** * Cancels editing. This method calls <code>fireEditingCanceled</code>. */public void cancelCellEditing() {fireEditingCanceled();}/** * When an action is performed, editing is ended. *  * @param e *            the action event * @see #stopCellEditing */public void actionPerformed(ActionEvent e) {ConditionValueEditor.this.stopCellEditing();}/** * When an item's state changes, editing is ended. *  * @param e *            the action event * @see #stopCellEditing */public void itemStateChanged(ItemEvent e) {ConditionValueEditor.this.stopCellEditing();}}}