You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
349 lines
9.1 KiB
349 lines
9.1 KiB
package com.fr.design.gui.ilist; |
|
|
|
import com.fr.design.gui.NameInspector; |
|
import com.fr.design.gui.itextfield.UITextField; |
|
import com.fr.general.GeneralUtils; |
|
import com.fr.general.NameObject; |
|
import com.fr.stable.Nameable; |
|
import com.fr.stable.StringUtils; |
|
import com.fr.stable.core.PropertyChangeAdapter; |
|
|
|
import javax.swing.ListModel; |
|
import javax.swing.event.CellEditorListener; |
|
import javax.swing.event.ChangeEvent; |
|
import java.util.ArrayList; |
|
import java.util.Vector; |
|
import java.awt.Component; |
|
import java.awt.Rectangle; |
|
import java.awt.event.FocusEvent; |
|
import java.awt.event.FocusListener; |
|
|
|
public class JNameEdList extends UIList implements CellEditorListener { |
|
private static final int ICON_WIDTH = 20; |
|
private boolean editable = true; |
|
|
|
// kunsnat: 是否强制ListName是数字 (int型) |
|
private boolean isNameShouldNumber = false; |
|
|
|
transient protected ListCellEditor cellEditor; |
|
transient protected Component editorComp; |
|
transient protected int editingIndex; |
|
private PropertyChangeAdapter editingListner; |
|
private java.util.List<ModNameActionListener> ll = new ArrayList<ModNameActionListener>(); |
|
/* |
|
* 编辑第index个item |
|
*/ |
|
private String oldName; |
|
|
|
private boolean replaceEmptyName = true; |
|
|
|
public JNameEdList(ListModel dataModel) { |
|
super(dataModel); |
|
} |
|
|
|
public JNameEdList(final Object[] listData) { |
|
super(listData); |
|
} |
|
|
|
public JNameEdList(final Vector<?> listData) { |
|
super(listData); |
|
} |
|
|
|
public JNameEdList() { |
|
super(); |
|
} |
|
|
|
/* |
|
* Sets是否可编辑 |
|
*/ |
|
public void setEditable(boolean editable) { |
|
this.editable = editable; |
|
} |
|
|
|
/** |
|
* 是否可编辑 |
|
* |
|
* @return 是则返回true |
|
*/ |
|
public boolean isEditable() { |
|
return this.editable; |
|
} |
|
|
|
public void setReplaceEmptyName(boolean replaceEmptyName) { |
|
this.replaceEmptyName = replaceEmptyName; |
|
} |
|
|
|
public void setNameShouldNumber(boolean isNameShouldNumber) { |
|
this.isNameShouldNumber = isNameShouldNumber; |
|
} |
|
|
|
/** |
|
* 是否强制ListName是数字 (int型) |
|
* |
|
* @return 是则返回true |
|
*/ |
|
public boolean isNameShouldNumber() { |
|
return isNameShouldNumber; |
|
} |
|
|
|
/** |
|
* 添加名字改变时的listener |
|
* |
|
* @param l 监听器 |
|
*/ |
|
public void addModNameActionListener(ModNameActionListener l) { |
|
ll.add(l); |
|
} |
|
|
|
/** |
|
* 编辑时的监听器 |
|
* |
|
* @param l 监听器 |
|
*/ |
|
public void addEditingListner(PropertyChangeAdapter l) { |
|
this.editingListner = l; |
|
} |
|
|
|
/** |
|
* 移除某名字改变时的listener |
|
* |
|
* @param l 监听器 |
|
*/ |
|
public void removeModNameActionListener(ModNameActionListener l) { |
|
ll.remove(l); |
|
} |
|
|
|
public ListCellEditor getCellEditor() { |
|
if (cellEditor == null) { |
|
UITextField editField = new UITextField(); |
|
if (editingListner != null) { |
|
editField.addFocusListener(new FocusListener() { |
|
|
|
@Override |
|
public void focusLost(FocusEvent e) { |
|
editingListner.propertyChange(); |
|
|
|
} |
|
|
|
@Override |
|
public void focusGained(FocusEvent e) { |
|
// TODO Auto-generated method stub |
|
|
|
} |
|
}); |
|
} |
|
cellEditor = new DefaultListCellEditor(editField) { |
|
public boolean stopCellEditing() { |
|
boolean isTrue = super.stopCellEditing(); |
|
stopEditing(); |
|
|
|
return isTrue; |
|
} |
|
}; |
|
cellEditor.addCellEditorListener(this); |
|
} |
|
|
|
return cellEditor; |
|
} |
|
|
|
protected void doAfterLostFocus() { |
|
|
|
} |
|
|
|
public void setCellEditor(ListCellEditor editor) { |
|
this.cellEditor = editor; |
|
} |
|
|
|
/* |
|
* 取得index节点的名字 |
|
*/ |
|
public String getNameAt(int index) { |
|
Nameable nameable = ((ListModelElement) getModel().getElementAt(index)).wrapper; |
|
if (nameable != null) { |
|
return nameable.getName(); |
|
} |
|
|
|
return null; |
|
} |
|
|
|
public Object getType(int index) { |
|
Nameable nameable = ((ListModelElement) getModel().getElementAt(index)).wrapper; |
|
if (nameable instanceof NameObject) { |
|
return ((NameObject) nameable).getObject(); |
|
} |
|
return null; |
|
} |
|
|
|
public void setIllegalIndex(int index) { |
|
setNameAt(NameInspector.ILLEGAL_NAME_HOLDER, index); |
|
this.repaint(); |
|
} |
|
|
|
public void setNameAt(String name, int index) { |
|
ListModelElement element = (ListModelElement) getModel().getElementAt(index); |
|
modifyNameable(element.wrapper, name, index); |
|
} |
|
|
|
private void modifyNameable(Nameable nameable, String name, int index) { |
|
if (nameable != null) { |
|
String oldName = nameable.getName(); |
|
if (isNameShouldNumber()) { |
|
Number number = GeneralUtils.string2Number(name); |
|
if (number == null) { |
|
nameable.setName(oldName); |
|
} else { |
|
int newName = number.intValue(); |
|
nameable.setName(String.valueOf(newName)); |
|
} |
|
} else { |
|
nameable.setName(name); |
|
} |
|
for (int i = 0, len = ll.size(); i < len; i++) { |
|
ll.get(i).nameModed(index, oldName, name); |
|
} |
|
} |
|
} |
|
|
|
/** |
|
* 编辑第index项 |
|
* |
|
* @param index 序号 |
|
* @return 成功返回true |
|
*/ |
|
public boolean editItemAt(int index) { |
|
// 如果不可编辑,返回 |
|
if (!this.editable) { |
|
return false; |
|
} |
|
|
|
if (cellEditor != null && !cellEditor.stopCellEditing()) { |
|
return false; |
|
} |
|
if (index < 0 || index >= this.getModel().getSize()) { |
|
return false; |
|
} |
|
|
|
ListCellEditor editor = getCellEditor(); |
|
Object value = editor.getCellEditorValue(); |
|
if (!StringUtils.isBlank(value.toString())) { |
|
oldName = value.toString(); |
|
} |
|
editorComp = prepareEditor(editor, index); |
|
if (editorComp == null) { |
|
return false; |
|
} |
|
Rectangle rect = this.getCellBounds(index, index); |
|
// alex:所有的JNameEdList都有Icon,空出前面20 * 20的位置就是放的Icon |
|
rect.setRect(createRect(rect, getIconWidth())); |
|
|
|
editorComp.setBounds(rect); |
|
add(editorComp); |
|
editorComp.validate(); |
|
editorComp.requestFocus(); |
|
if (editorComp instanceof UITextField) { |
|
((UITextField) editorComp).selectAll(); |
|
} |
|
|
|
setEditingIndex(index); |
|
|
|
return true; |
|
} |
|
|
|
public int getIconWidth() { |
|
return ICON_WIDTH; |
|
} |
|
|
|
public Rectangle createRect(Rectangle rect, int iconWidth) { |
|
return new Rectangle(rect.x + iconWidth, rect.y, rect.width - iconWidth, rect.height); |
|
} |
|
|
|
public String getEditingName() { |
|
return (String) getCellEditor().getCellEditorValue(); |
|
} |
|
|
|
/* |
|
* 根据ListCellEditor取得编辑器的Component |
|
*/ |
|
private Component prepareEditor(ListCellEditor cellEditor, int index) { |
|
String name = getNameAt(index); |
|
boolean isSelected = this.isSelectedIndex(index); |
|
|
|
return cellEditor.getListCellEditorComponent(this, name, isSelected, index); |
|
} |
|
|
|
/* |
|
* 记录正在编辑的index |
|
*/ |
|
private void setEditingIndex(int idx) { |
|
editingIndex = idx; |
|
} |
|
|
|
/** |
|
* 编辑取消 |
|
* |
|
* @param e 事件 |
|
*/ |
|
public void editingCanceled(ChangeEvent e) { |
|
removeComp(); |
|
} |
|
|
|
/** |
|
* 编辑结束 |
|
* |
|
* @param e 事件 |
|
*/ |
|
public void editingStopped(ChangeEvent e) { |
|
doAfterLostFocus(); |
|
stopEditing(); |
|
} |
|
|
|
/** |
|
* 停止编辑事件 |
|
*/ |
|
public void stopEditing() { |
|
ListCellEditor editor = getCellEditor(); |
|
if (editor != null && editorComp != null) { |
|
Object value = editor.getCellEditorValue(); |
|
String name = StringUtils.isBlank(value.toString()) && replaceEmptyName ? oldName : value.toString(); |
|
setNameAt(name, editingIndex); |
|
removeComp(); |
|
doAfterStopEditing(); |
|
} |
|
} |
|
|
|
protected void doAfterStopEditing() { |
|
// default: do nothing |
|
} |
|
|
|
public String[] getAllNames() { |
|
int length = this.getModel().getSize(); |
|
String[] names = new String[length]; |
|
for (int i = 0; i < length; i++) { |
|
names[i] = getNameAt(i); |
|
} |
|
return names; |
|
} |
|
|
|
public Object[] getAllTypes() { |
|
int length = this.getModel().getSize(); |
|
Object[] types = new Object[length]; |
|
for (int i = 0; i < length; i++) { |
|
types[i] = getType(i); |
|
} |
|
return types; |
|
} |
|
|
|
|
|
/* |
|
* 移除编辑器的Component |
|
*/ |
|
private void removeComp() { |
|
if (editorComp != null) { |
|
remove(editorComp); |
|
} |
|
Rectangle cellRect = this.getCellBounds(editingIndex, editingIndex); |
|
setEditingIndex(-1); |
|
editorComp = null; |
|
repaint(cellRect); |
|
} |
|
} |