# JTree und JCheckbox Problem



## internetscout (19. Aug 2007)

Hi, 
ich habe ein kleines Problem mit dem Jtree und Jcheckbox. 
Ich möchte einen JTree aufbauen mit jCheckboxen. Es soll erstmal nur eine Ebene sein. (also nur leafs).  Wenn Ich eine Node anwähle, dann soll die Checkbox nicht angehackt werden. Erst wenn ich die Checkbox anklicke soll diese aktiviert werden
Ich habe schon gegoogled und entweder ein oversized Lösung gefunden oder welche, die nicht funktionieren. Ein Beispiel war ganz ok, bin damit ziemlich weit gekommen, aber es funktioniert noch nicht so. Ich lese die Nodes aus einer datei ein. Am Ende sieht das schon ziemlich gut aus. Ich habe auch einen Tree mit Checkboxen, kann diese aber nicht selektieren. Ich habe auch den Verdacht, dass wenn ich die Node anwähle automatisch die Checkbox selektiert wird. Was habe ich vergessen, damit die Checkboxen selektiert werden können? Muss ich in dem Fall einen MouseListener  implementieren? Wie muss ich den Quelltext anpassen, damit ich die node anwählen kann, die Checkbox aber nicht gesetzt wird.

Danke Schon mal im voraus

Internetscout

Ps: Kennt jemand ein Buch, was sich intensiv mit Jtree beschäftigt Bei Büchern  wie "Handbuch der Java Programmierung" oder "Java ist auch eine Insel" kommt der jtree für meine Begriffe zu kurz. 

  Achja den Codeschnipsel hätte ich beinahe vergessen. 



```
String line="";
String str=",";
String log[]=new String[200];
DefaultMutableTreeNode top =  new DefaultMutableTreeNode("Tree");
DefaultMutableTreeNode child = null;
int i=0;
try {
    BufferedReader f = new BufferedReader(new FileReader("config.ini"));
    while ((line =f.readLine())!=null){
        log[i] = line.substring(0,line.indexOf(str));
        System.out.println(log[i]);
        child = new DefaultMutableTreeNode(log[i]);
        top.add(child);
        i++;
     
    }
}
  catch (IOException e){
      System.err.println(e.toString());
  } 
DefaultTreeModel treeModel = new DefaultTreeModel(top);
jTree1.setModel(treeModel);
jTree1.setCellRenderer(new CheckBoxNodeRenderer());
jTree1.setCellEditor(new CheckBoxNodeEditor(jTree1));
jTree1.setEditable(true);



  class CheckBoxNodeRenderer implements TreeCellRenderer {
  private JCheckBox leafRenderer = new JCheckBox();
  private DefaultTreeCellRenderer nonLeafRenderer = new DefaultTreeCellRenderer();
  Color selectionBorderColor, selectionForeground, selectionBackground,
      textForeground, textBackground;

  protected JCheckBox getLeafRenderer() {
    return leafRenderer;
  }

  public CheckBoxNodeRenderer() {
    Font fontValue;
    fontValue = UIManager.getFont("Tree.font");
    if (fontValue != null) {
      leafRenderer.setFont(fontValue);
    }
    Boolean booleanValue = (Boolean) UIManager
        .get("Tree.drawsFocusBorderAroundIcon");
    leafRenderer.setFocusPainted((booleanValue != null)
        && (booleanValue.booleanValue()));

    selectionBorderColor = UIManager.getColor("Tree.selectionBorderColor");
    selectionForeground = UIManager.getColor("Tree.selectionForeground");
    selectionBackground = UIManager.getColor("Tree.selectionBackground");
    textForeground = UIManager.getColor("Tree.textForeground");
    textBackground = UIManager.getColor("Tree.textBackground");
  }

  public Component getTreeCellRendererComponent(JTree tree, Object value, boolean selected, boolean expanded, boolean leaf, int row,
      boolean hasFocus) {

    Component returnValue;
    if (leaf) {

      String stringValue = tree.convertValueToText(value, selected,
          expanded, leaf, row, false);
      leafRenderer.setText(stringValue);
      leafRenderer.setSelected(false);

      leafRenderer.setEnabled(tree.isEnabled());

      if (selected) {
        leafRenderer.setForeground(selectionForeground);
        leafRenderer.setBackground(selectionBackground);
      } else {
        leafRenderer.setForeground(textForeground);
        leafRenderer.setBackground(textBackground);
      }

      if ((value != null) && (value instanceof DefaultMutableTreeNode)) {
        Object userObject = ((DefaultMutableTreeNode) value)
            .getUserObject();
        if (userObject instanceof CheckBoxNode) {
          CheckBoxNode node = (CheckBoxNode) userObject;
          leafRenderer.setText(node.getText());
          leafRenderer.setSelected(node.isSelected());
        }
      }
      returnValue = leafRenderer;
    } else {
      returnValue = nonLeafRenderer.getTreeCellRendererComponent(tree,
          value, selected, expanded, leaf, row, hasFocus);
    }
    return returnValue;
  }
}

class CheckBoxNodeEditor extends AbstractCellEditor implements TreeCellEditor {

  CheckBoxNodeRenderer renderer = new CheckBoxNodeRenderer();

  ChangeEvent changeEvent = null;

  JTree tree;

  public CheckBoxNodeEditor(JTree tree) {
    this.tree = tree;
  }

  public Object getCellEditorValue() {
    JCheckBox checkbox = renderer.getLeafRenderer();
    CheckBoxNode checkBoxNode = new CheckBoxNode(checkbox.getText(),
        checkbox.isSelected());
    return checkBoxNode;
  }
  public boolean isCellEditable(EventObject event) {
    boolean returnValue = false;
    if (event instanceof MouseEvent) {
      MouseEvent mouseEvent = (MouseEvent) event;
      TreePath path = tree.getPathForLocation(mouseEvent.getX(),
          mouseEvent.getY());
      if (path != null) {
        Object node = path.getLastPathComponent();
        if ((node != null) && (node instanceof DefaultMutableTreeNode)) {
          DefaultMutableTreeNode treeNode = (DefaultMutableTreeNode) node;
          Object userObject = treeNode.getUserObject();
          returnValue = ((treeNode.isLeaf()) && (userObject instanceof CheckBoxNode));
        }
      }
    }
    return returnValue;
  }
  public Component getTreeCellEditorComponent(JTree tree, Object value,
      boolean selected, boolean expanded, boolean leaf, int row) {

    Component editor = renderer.getTreeCellRendererComponent(tree, value,
        true, expanded, leaf, row, true);

    // editor always selected / focused
    ItemListener itemListener = new ItemListener() {
      public void itemStateChanged(ItemEvent itemEvent) {
        if (stopCellEditing()) {
          fireEditingStopped();
        }
      }
    };
    if (editor instanceof JCheckBox) {
      ((JCheckBox) editor).addItemListener(itemListener);
    }

    return editor;
  }
}

class CheckBoxNode {
  String text;

  boolean selected;

  public CheckBoxNode(String text, boolean selected) {
    this.text = text;
    this.selected = selected;
  }

  public boolean isSelected() {
    return selected;
  }

  public void setSelected(boolean newValue) {
    selected = newValue;
  }

  public String getText() {
    return text;
  }

  public void setText(String newValue) {
    text = newValue;
  }

  public String toString() {
    return getClass().getName() + "[" + text + "/" + selected + "]";
  }
}
```
[/code]


----------



## André Uhres (20. Aug 2007)

Ich hab mal versucht, den JTree nicht editable zu machen und setEditable(true) erst im Renderer aufzurufen,
aber das funktioniert leider auch nicht immer


----------



## Dit (23. Aug 2007)

stehe auch gerade einem änlichen Problem, wir wollen es so machen wie bei den meisten Installationen, wenn man den Oberpunkt anklickt (Checkbox auswählt) dann sollen alle darunter liegenden Punkte auch selektiert werden.

Habe aber noch nicht lang gesucht, bin hier auf den ersten hinweis gestoßen, sollte ich aber was raus bekommen werd ich es euch wissen lassen.

Gruß


----------



## André Uhres (23. Aug 2007)

Dit hat gesagt.:
			
		

> ..wenn man den Oberpunkt anklickt (Checkbox auswählt) dann sollen alle darunter liegenden Punkte auch selektiert werden..


Hab hier mal so was gefunden:
http://www.codeguru.com/java/articles/185.shtml
Aber das Problem von internetscout ist damit nicht gelöst.


----------



## Dit (24. Aug 2007)

danke, werde mich mal mit auseinandersetzen.
InternetScout hat natürlich ein Problem das weit über meinem liegt.

Aber wie gesagt sollte ich irgendwas beim suchen finden, was dir zu deiner Lösung helfen könnte, dann werde ich es hier posten! :toll:


----------

