java jtable cell editor
fácil y rápido JTree Cell Editor (2)
Tengo un JTree con un TreeModel personalizado y un TreeRenderer personalizado. El Modelo de árbol contiene un grupo de objetos de diferentes tipos. Uno de estos tipos se muestra de forma diferente a los demás: el texto que se muestra es una concatenación de dos campos del objeto. Cuando edito la celda, quiero actualizar uno de estos campos con el texto editado. Hasta ahora lo hice funcionar bastante bien.
Mi problema: es confuso cuando el texto, que se muestra durante la edición, es el valor total concatenado de 2 campos, aunque en realidad solo está editando uno de los campos. Por lo tanto, quiero mostrar solo el contenido del campo que está editando cuando el usuario comienza a editar.
Traté de hacer esto con un CellEditor personalizado, y vi la forma en que se supone que debe funcionar y el enfoque parece excesivo en mi caso. Solo quiero modificar el texto que se muestra en uno de muchos casos, así que, naturalmente, quiero implementar eso, y no todo un CellEditor para todo el contenido de mi árbol.
¿Existe una manera más rápida y fácil de hacerlo, o tengo que usar un editor personalizado?
Gracias
No hay forma de evitar un editor personalizado y es la solución más corta posible :-) Además, necesitará algunos medios en el ámbito de datos que puedan interpretar el valor de edición según corresponda y actualizarse a sí mismo, fi un nodo personalizado.
Fi (lo comentaré más tarde, mi cojo Firefox en esta máquina me está conduciendo por las paredes)
/**
* Basic code stolen from @trashgod at
* @see http://.com/a/11113648/230513
*/
public class TreeEditDemo extends JPanel {
private JTree tree;
private DefaultMutableTreeNode root;
private DefaultTreeCellEditor editor;
public TreeEditDemo() {
super.setLayout(new GridLayout());
root = new DefaultMutableTreeNode("Nodes");
root.add(new MyResourceNode(new Resource("one", "first")));
root.add(new MyResourceNode(new Resource("two", "first")));
tree = new JTree(root);
tree.setEditable(true);
editor = new MyTreeCellEditor(tree,
(DefaultTreeCellRenderer) tree.getCellRenderer());
tree.setCellEditor(editor);
this.add(new JScrollPane(tree));
}
private static class MyTreeCellEditor extends DefaultTreeCellEditor {
public MyTreeCellEditor(JTree tree, DefaultTreeCellRenderer renderer) {
super(tree, renderer);
}
@Override
public Component getTreeCellEditorComponent(JTree tree, Object value,
boolean isSelected, boolean expanded, boolean leaf, int row) {
if (value instanceof MyResourceNode) {
value = ((MyResourceNode) value).getName();
}
return super.getTreeCellEditorComponent(tree, value, isSelected, expanded,
leaf, row);
}
@Override
public boolean isCellEditable(EventObject e) {
return super.isCellEditable(e)
&& ((TreeNode) lastPath.getLastPathComponent()).isLeaf();
}
}
public static class MyResourceNode extends DefaultMutableTreeNode {
/**
* @param resource
*/
public MyResourceNode(Resource resource) {
super(resource);
}
@Override
public void setUserObject(Object userObject) {
if (userObject instanceof String) {
setName((String) userObject);
} else if (userObject instanceof Resource) {
super.setUserObject(userObject);
}
}
public void setName(String name) {
if (getUserObject() != null) {
getUserObject().setName(name);
}
}
public String getName() {
if (getUserObject() != null) {
return getUserObject().getName();
}
return null;
}
@Override
public Resource getUserObject() {
return (Resource) super.getUserObject();
}
}
private static class Resource {
String name;
private String category;
public Resource(String name, String category) {
this.name = name;
this.category = category;
}
public void setName(String name) {
this.name = name;
}
public String getName() {
return name;
}
@Override
public String toString() {
// BEWARE: don''t do this in production code!
return name + " (" + category + ")";
}
}
private void display() {
JFrame f = new JFrame("TreeEditorDemo");
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.add(this);
f.pack();
f.setLocationRelativeTo(null);
f.setVisible(true);
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
new TreeEditDemo().display();
}
});
}
}
Se requiere un editor personalizado. MyTreeCellEditor
, ilustrado aquí , muestra un enfoque. Actualiza un atributo arbitrario de un userObject
, que se denomina Resource
y se mantiene en un DefaultMutableTreeNode
. Como el atributo es texto, también usa DefaultTreeCellRenderer
. Su TreeModel
personalizado probablemente maneje un userObject
similar que sea el padre de sus "objetos de diferentes tipos".