2012-12-27 87 views
2

我正在使用CheckBoxTree組件來獲取一種特殊的JTree複選框。但是,我希望能夠在高級別節點上沒有複選框,因爲它們不應該被檢查,它們只是「分支的名稱」。這裏的樹的一個簡單的例子:從CheckBoxTree節點中刪除複選框

元數據 - 產品 - PROD甲 - PROD乙 - 等 - 模型 - 等

節點 「元數據」 是這樣的TreeModel的根。由於使用了方便的setRootVisible方法(如JTree),此節點不可見。但除了使根不可見外,我還希望刪除第二級複選框。所以基本上,應該只有從產品A,產品B等等向下的級別(可以降低幾個級別)的複選框。但我仍然想要二級標籤。

我試圖實現自定義CheckboxTreecellRenderer根據該網站描述checkboxtree組件:

http://www.javaworld.com/javaworld/jw-09-2007/jw-09-checkboxtree.html?page=3

不幸的是,這是行不通的。與網站上的示例相比,我試着移動添加標籤和按鈕(我不打算使用單選按鈕,只是使用它來嘗試刪除標籤以保持簡單,但我仍然要使用複選框,如果我得到這個工作以某種方式)。我移動它們是爲了試圖設置一個按鈕,只有當節點有元數據節點作爲其父節點時,才能從第二級刪除按鈕。

但這沒有奏效。令人驚訝的是,這個概念本身似乎工作,因爲button.setEnabled(false); (註釋如下)確實有效。這將禁用正確級別的按鈕。但是,如果我嘗試不添加按鈕有我沒有得到任何按鈕的任何地方......

/* 
* To change this template, choose Tools | Templates 
* and open the template in the editor. 
*/ 
package se.expertinfo.ditaplugin; 

import it.cnr.imaa.essi.lablib.gui.checkboxtree.CheckboxTree; 
import it.cnr.imaa.essi.lablib.gui.checkboxtree.CheckboxTreeCellRenderer; 
import it.cnr.imaa.essi.lablib.gui.checkboxtree.TreeCheckingModel; 
import java.awt.Color; 
import java.awt.Component; 
import java.awt.FlowLayout; 
import javax.swing.JLabel; 
import javax.swing.JPanel; 
import javax.swing.JRadioButton; 
import javax.swing.JTree; 
import javax.swing.UIManager; 
import javax.swing.tree.TreePath; 

/** 
* 
* @author Anders 
*/ 
public class CustomTreeCellRenderer implements CheckboxTreeCellRenderer { 

    JPanel panel = new JPanel(); 
    JLabel label = new JLabel(); 
    JRadioButton button = new JRadioButton(); 

    public CustomTreeCellRenderer() { 
     label.setFocusable(true); 
     label.setOpaque(true); 
     panel.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); 
//  panel.add(button); 
//  panel.add(label); 
     button.setBackground(UIManager.getColor("Tree.textBackground")); 
     panel.setBackground(UIManager.getColor("Tree.textBackground")); 
    } 

    @Override 
    public Component getTreeCellRendererComponent(JTree tree, Object value, boolean selected, boolean expanded, boolean leaf, int row, 
      boolean hasFocus) { 
     label.setText(value.toString()); 
     if (selected) { 
      label.setBackground(UIManager.getColor("Tree.selectionBackground")); 
     } else { 
      label.setBackground(UIManager.getColor("Tree.textBackground")); 
     } 
     TreeCheckingModel checkingModel = ((CheckboxTree) tree).getCheckingModel(); 

     TreePath path = tree.getPathForRow(row); 


     boolean enabled = checkingModel.isPathEnabled(path); 
     boolean checked = checkingModel.isPathChecked(path); 
     boolean grayed = checkingModel.isPathGreyed(path); 

     button.setEnabled(enabled); 

     if (path != null) { 
      TreePath parent = path.getParentPath(); 
      if (parent != null) { 
       if (parent.getLastPathComponent().toString().equalsIgnoreCase("metadata")) { 
//     button.setEnabled(false);      
        panel.add(label); 
       } else {      
        panel.add(button); 
        panel.add(label); 
        button.setSelected(checked); 
       } 
      } 
     } 


     if (grayed) { 
      label.setForeground(Color.lightGray); 
     } else { 
      label.setForeground(Color.black); 
     } 
     button.setSelected(checked); 
     return panel; 
    } 

    @Override 
    public boolean isOnHotspot(int x, int y) { 
     return (button.getBounds().contains(x, y)); 
    } 
} 

回答

2

example使用isLeaf()isCellEditable()實施,限制編輯只有葉節點。

附錄:要阻止編輯超過某個級別,可以使用謂詞(如:path.getPathCount() > 2)檢查路徑上的元素數量。

+0

謝謝,但我已經想到了,這還不夠。我希望其他節點可以編輯,因爲如前所述樹可以深入幾個層次。它只是我想要禁用的第二級別(低於已經隱藏的根目錄),最好從中刪除複選框。 – Anders

+0

我已經闡述過了; 'isCellEditable()'控制哪些節點獲得複選框。 – trashgod

+0

謝謝,這工作得很好:-) – Anders