• category: swing folder: TreeComboBox title: JComboBoxのItemをTree状に表示する tags: [JComboBox, TreeModel] author: aterai pubdate: 2011-07-11T15:16:42+09:00 description: JComboBoxのドロップダウンリストに表示するItemをTree状に配置します。 image: https://lh6.googleusercontent.com/-5GlQEjeLoH8/ThqUIL9b4UI/AAAAAAAAA_E/9h5dxYzSSm8/s800/TreeComboBox.png

概要

JComboBoxのドロップダウンリストに表示するItemTree状に配置します。

サンプルコード

class TreeComboBox extends JComboBox {
  public TreeComboBox() {
    super();
    setRenderer(new DefaultListCellRenderer() {
      @Override public Component getListCellRendererComponent(
          JList list, Object value, int index,
          boolean isSelected, boolean cellHasFocus) {
        JComponent c;
        if (value instanceof DefaultMutableTreeNode) {
          DefaultMutableTreeNode node = (DefaultMutableTreeNode) value;
          int indent = 2 + (index < 0 ? 0 : (node.getPath().length - 2) * 16);
          if (node.isLeaf()) {
            c = (JComponent) super.getListCellRendererComponent(
                list, value, index, isSelected, cellHasFocus);
          } else {
            c = (JComponent) super.getListCellRendererComponent(
                list, value, index, false, false);
            JLabel l = (JLabel) c;
            l.setForeground(Color.WHITE);
            l.setBackground(Color.GRAY.darker());
          }
          c.setBorder(BorderFactory.createEmptyBorder(0, indent, 0, 0));
        } else {
          c = (JComponent) super.getListCellRendererComponent(
              list, value, index, isSelected, cellHasFocus);
        }
        return c;
      }
    });
    Action up = new AbstractAction() {
      @Override public void actionPerformed(ActionEvent e) {
        int si = getSelectedIndex();
        for (int i = si - 1; i >= 0; i--) {
          Object o = getItemAt(i);
          if (o instanceof TreeNode && ((TreeNode) o).isLeaf()) {
            setSelectedIndex(i);
            break;
          }
        }
      }
    };
    Action down = new AbstractAction() {
      @Override public void actionPerformed(ActionEvent e) {
        int si = getSelectedIndex();
        for (int i = si + 1; i < getModel().getSize(); i++) {
          Object o = getItemAt(i);
          if (o instanceof TreeNode && ((TreeNode) o).isLeaf()) {
            setSelectedIndex(i);
            break;
          }
        }
      }
    };
    ActionMap am = getActionMap();
    am.put("selectPrevious3", up);
    am.put("selectNext3", down);
    InputMap im = getInputMap();
    im.put(KeyStroke.getKeyStroke(KeyEvent.VK_UP, 0),      "selectPrevious3");
    im.put(KeyStroke.getKeyStroke(KeyEvent.VK_KP_UP, 0),   "selectPrevious3");
    im.put(KeyStroke.getKeyStroke(KeyEvent.VK_DOWN, 0),    "selectNext3");
    im.put(KeyStroke.getKeyStroke(KeyEvent.VK_KP_DOWN, 0), "selectNext3");
  }
  private boolean isNotSelectableIndex = false;
  @Override public void setPopupVisible(boolean v) {
    if (!v && isNotSelectableIndex) {
      isNotSelectableIndex = false;
    } else {
      super.setPopupVisible(v);
    }
  }
  @Override public void setSelectedIndex(int index) {
    Object o = getItemAt(index);
    if (o instanceof TreeNode && !((TreeNode) o).isLeaf()) {
      isNotSelectableIndex = true;
    } else {
      super.setSelectedIndex(index);
    }
  }
}
View in GitHub: Java, Kotlin

解説

上記のサンプルでは、TreeModelから取得したTreeNodeJComboBoxItemとして、ドロップダウンリストに表示しています。

参考リンク

コメント