JTree通过单击行上的任何位置来选择节点

我从这里获取的代码可以通过单击行上的任何位置来选择JTree行。 它在单行选择模式下工作正常。 但是,我不知道如何修改它以处理多行选择。 当用户进行多重选择时(例如在按住鼠标左键的同时按住shift键或控制键),如何区分这种情况?

import java.awt.Rectangle;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;

import javax.swing.JFrame;
import javax.swing.JTree;
import javax.swing.SwingUtilities;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.TreeNode;


@SuppressWarnings("serial")
public class NavTree extends JTree {

    private boolean                 fWholeRowSelectionEnabled;
    private MouseListener           fRowSelectionListener;
    final NavTree                   fThis;

    public NavTree(TreeNode rootNode) {
        super(rootNode);
        fThis = this;
        init();
    }
    public NavTree() {
        fThis = this;
        init();
    }

    private void init() {
        //setCellRenderer(new NavTreeCellRenderer());
        fRowSelectionListener = new MouseAdapter() {

            public void mousePressed(MouseEvent e) {
                if (SwingUtilities.isLeftMouseButton(e)) {
                    int closestRow = fThis.getClosestRowForLocation(
                            e.getX(), e.getY());
                    Rectangle closestRowBounds = fThis.getRowBounds(closestRow);
                    if(e.getY() >= closestRowBounds.getY() && 
                            e.getY() < closestRowBounds.getY() + 
                            closestRowBounds.getHeight()) {
                        if(e.getX() > closestRowBounds.getX() && 
                                closestRow < fThis.getRowCount()){

                                                    fThis.setSelectionRow(closestRow);
                                                }

                    } else
                        fThis.setSelectionRow(-1);
                }
            }

        };
        setWholeRowSelectionEnabled(true);
    }

    public void setWholeRowSelectionEnabled(boolean wholeRowSelectionEnabled) {
        fWholeRowSelectionEnabled = wholeRowSelectionEnabled;
        if (fWholeRowSelectionEnabled)
            addMouseListener(fRowSelectionListener);
        else
            removeMouseListener(fRowSelectionListener);
    }

    public boolean isWholeRowSelectionEnabled() {
        return fWholeRowSelectionEnabled;
    }

    public static void main(String[] args) {
        JFrame frame = new JFrame();
        DefaultMutableTreeNode root = new DefaultMutableTreeNode("Root");
        root.add(new DefaultMutableTreeNode("Child 1"));
        root.add(new DefaultMutableTreeNode("Child 2"));
        root.add(new DefaultMutableTreeNode("Child 3"));
        NavTree tree = new NavTree(root);
        frame.add(tree);
        frame.setSize(200, 300);
        frame.setVisible(true);
    }
}

使用MouseEvent的修饰键信息。 有关更多信息,请参阅MouseEvent#getModifiersEx


PS:监听器注册包含一个错误

public void setWholeRowSelectionEnabled(boolean wholeRowSelectionEnabled) {
    fWholeRowSelectionEnabled = wholeRowSelectionEnabled;
    if (fWholeRowSelectionEnabled)
        addMouseListener(fRowSelectionListener);
    else
        removeMouseListener(fRowSelectionListener);
}

将属性wholeRowSelectionEnabled设置为true应只注册侦听器一次。 如果该属性设置为true多次,您的代码会一次又一次地添加侦听器。 我的意思是,财产制定者应该是幂等的。

一个quickfix可以先删除它,如果启用则添加它

public void setWholeRowSelectionEnabled(boolean wholeRowSelectionEnabled) {
    removeMouseListener(fRowSelectionListener);
    fWholeRowSelectionEnabled = wholeRowSelectionEnabled;
    if (fWholeRowSelectionEnabled)
        addMouseListener(fRowSelectionListener);
}
链接地址: http://www.djcxy.com/p/23857.html

上一篇: JTree select node by clicking anywhere on the row

下一篇: java swing clear the event queue