• category: swing folder: ListMouseSelection title: JListをマウスクリックのみで複数選択する tags: [JList, MouseListener] author: aterai pubdate: 2011-07-18T17:21:18+09:00 description: JListをアイテムをマウスクリックだけで複数選択できるように設定します。 image: https://lh6.googleusercontent.com/-wj2xm8BlBbA/TiPrjr1sQ5I/AAAAAAAAA_c/NiXO891B5fs/s800/ListMouseSelection.png hreflang:
       href: https://java-swing-tips.blogspot.com/2012/04/select-multiple-items-in-jlist-by.html
       lang: en

概要

概要

JListをアイテムをマウスクリックだけで複数選択できるように設定します。

サンプルコード

サンプルコード

JList list = new JList(model) {
  private ClearSelectionListener listener;
  @Override public void setSelectionInterval(int anchor, int lead) {
    if (anchor == lead && lead >= 0 && anchor >= 0) {
      if (listener.isDragging) {
        addSelectionInterval(anchor, anchor);
      } else if (!listener.isInCellDragging) {
        if (isSelectedIndex(anchor)) {
          removeSelectionInterval(anchor, anchor);
        } else {
          addSelectionInterval(anchor, anchor);
        }
        listener.isInCellDragging = true;
      }
    } else {
      super.setSelectionInterval(anchor, lead);
    }
  }
};
View in GitHub: Java, Kotlin

解説

解説

  • 左: Default
    • Ctrlキーを押しながらマウスクリックでリストアイテムの複数選択が可能
  • 中: MouseEvent
    • JList#processMouseEvent, JList#processMouseMotionEventをオーバーライドして、常にCtrlキーが押されている状態にする
    • マウスでアイテムをドラッグしても選択状態は変わらない
    • JListの空白部分をクリックした場合、アイテムの選択状態は変更せず(MouseEvent#consume())、フォーカスだけJListに移動
    • 参考: Swing - JList where mouse click acts like ctrl-mouse click
  • JList#processMouseEventJList#processMouseMotionEventをオーバーライドして常にCtrlキーが押されている状態に設定
  • マウスでアイテムをドラッグしても選択状態は変化しない
  • JListの空白部分をクリックした場合、アイテムの選択状態は変更せず(MouseEvent#consume())フォーカスだけJListに移動
  • 参考: Swing - JList where mouse click acts like ctrl-mouse click
    JList list = new JList(model) {
      @Override protected void processMouseMotionEvent(MouseEvent e) {
        super.processMouseMotionEvent(convertMouseEvent(e));
      }
    #spanadd
    
    #spanend
      @Override protected void processMouseEvent(MouseEvent e) {
        if (e.getID() == MouseEvent.MOUSE_PRESSED &&
            !getCellBounds(0, getModel().getSize() - 1).contains(e.getPoint())) {
          e.consume();
          requestFocusInWindow();
        } else {
          super.processMouseEvent(convertMouseEvent(e));
        }
      }
    #spanadd
    
    #spanend
      private MouseEvent convertMouseEvent(MouseEvent e) {
        //Swing - JList where mouse click acts like ctrl-mouse click
        //https://forums.oracle.com/thread/1351452
        // Swing - JList where mouse click acts like ctrl-mouse click
        // https://community.oracle.com/thread/1351452
        return new MouseEvent(
            (Component) e.getSource(),
            e.getID(), e.getWhen(),
            //e.getModifiers() | InputEvent.CTRL_MASK,
            //select multiple objects in OS X: Command+click
            //pointed out by nsby
            // e.getModifiers() | InputEvent.CTRL_MASK,
            // select multiple objects in OS X: Command+click
            // pointed out by nsby
            e.getModifiers() | Toolkit.getDefaultToolkit().getMenuShortcutKeyMask(),
            e.getX(), e.getY(),
            e.getXOnScreen(), e.getYOnScreen(),
            e.getClickCount(),
            e.isPopupTrigger(),
            e.getButton());
      }
    };
    
  • 右: SelectionInterval
    • JList#setSelectionIntervalをオーバーライドして、ひとつのアイテムのセルを選択した場合は、JList#addSelectionIntervalJList#removeSelectionIntervalを使用するように変更
    • マウスでアイテムをドラッグすると、選択状態になる
    • JList#setSelectionIntervalをオーバーライドしてひとつのアイテムのセルを選択した場合、JList#addSelectionIntervalJList#removeSelectionIntervalを使用するように変更
    • マウスでアイテム上をドラッグすると選択状態になる
    • ひとつのアイテムのセル内でのドラッグでは、選択状態を変更しない
    • 参考: Swing - Re: JList where mouse click acts like ctrl-mouse click
    • JListの空白部分をクリックした場合、アイテムの選択状態をすべてクリア(JListの選択を解除)
    • JListの空白部分をクリックした場合、アイテムの選択状態をすべてクリア

参考リンク

参考リンク

コメント

コメント