2009-03-31 11 views
5

Tengo un JTree que implementa lógica de selección múltiple.cómo configurar el modo de selección JTree "ctrl" para que esté siempre habilitado

Esto funciona muy bien cuando hago todas mis selecciones con la tecla del mouse + Ctrl presionada. Si el usuario hace selecciones con la tecla Ctrl sin presionar, rompe mi lógica.

No puedo ver por qué se rompe pero creo que una posible solución es indicar siempre TreeSelectionModel que la selección se ha realizado con la tecla Ctrl presionada.

¿Qué sugeriría?

+0

necesidad de aclarar algunas cosas . Entonces, presionar CTRL + clic izquierdo le permite seleccionar múltiples nodos en jtree, pero cuando solo hace clic, solo selecciona uno. Entonces, ¿qué quieres es tener el árbol de trabajo como ctrl siempre se presiona y simplemente seguir agregando selecciones en cada clic? – willcodejavaforfood

+0

@willcodejavaforfood - Exactamente. –

Respuesta

5

creo que he encontrado la solución

Va a necesitar extender JTree y DefaultTreeSelectionModel.

JTree métodos relevantes:

///////////////////////////////////////////////////// 
///////////////////////////////////////////////////// 
/// Implement selection using "adding" only logic. // 
///////////////////////////////////////////////////// 
///////////////////////////////////////////////////// 

@Override 
public void setSelectionPath(TreePath path) { 

    System.out.println("MLDebugJTree: setSelectionPath(" + path + ")"); 

    addSelectionPath(path); 

    return; 
    //super.setSelectionPath(path); 
} 

@Override 
public void setSelectionPaths(TreePath[] paths) { 

    System.out.println("MLDebugJTree: setSelectionPaths(" + paths + ")"); 

    addSelectionPaths(paths); 

    return; 
} 

@Override 
public void setSelectionRow(int row) { 

    System.out.println("MLDebugJTree: setSelectionRow(" + row + ")"); 

    addSelectionRow(row); 

    return; 
    //super.setSelectionRow(row); 
} 

@Override 
public void setSelectionRows(int[] rows) { 

    System.out.println("MLDebugJTree: setSelectionRows(" + rows + ")"); 

    addSelectionRows(rows); 

    return; 
    //super.setSelectionRows(rows); 
} 

DefaultSelectionModel métodos relevantes:

package com.ml.tree2.model.impl; 

import javax.swing.tree.DefaultTreeSelectionModel; 
import javax.swing.tree.TreePath; 

public class MLTreeSelectionModel extends DefaultTreeSelectionModel { 
private static final long serialVersionUID = -4270031800448415780L; 

@Override 
public void addSelectionPath(TreePath path) { 
    // Don't do overriding logic here because addSelectionPaths is ultimately called. 
    super.addSelectionPath(path); 
} 

@Override 
public void addSelectionPaths(TreePath[] paths) { 
    if(paths != null) { 
     for(TreePath path : paths) { 

      TreePath[] toAdd = new TreePath[1]; 
      toAdd[0] = path; 

      if (isPathSelected(path)) { 
       // If path has been previously selected REMOVE THE SELECTION. 
       super.removeSelectionPaths(toAdd); 
      } else { 
       // Else we really want to add the selection... 
       super.addSelectionPaths(toAdd); 
      } 
     } 
    } 
} 

HTH.

+0

gracias, no puedo decir lo suficiente, ¡esto me ahorró un montón de búsquedas! –

2

Otra solución sería la de extender simplemente BasicTreeUI y cambiar el comportamiento de selección para satisfacer sus necesidades:

public class MultiSelectionTreeUI extends BasicTreeUI 
{ 

    @Override 
    protected boolean isToggleSelectionEvent(MouseEvent event) 
    { 
     return SwingUtilities.isLeftMouseButton(event); 
    } 
} 

Y a continuación, establecer que la IU en su JTree:

JTree tree = new JTree(); 
tree.setUI(new MultiSelectionTreeUI()); 
+0

Volverá a 'BasicUI' en lugar de otro L & F (p.ex.' WindowsTreeUI') con esta solución, pero es el más limpio. –

Cuestiones relacionadas