是否可以使用java Swing DnD api启动鼠标按住拖动?

是否可以使用java Swing DnD api启动鼠标按住拖动?,java,swing,user-interface,drag-and-drop,Java,Swing,User Interface,Drag And Drop,在下面的示例中,有一种触发拖放的标准方法,即mousePress+mouseMove import javax.swing.*; import java.awt.datatransfer.StringSelection; import java.awt.dnd.DnDConstants; import java.awt.dnd.DragGestureListener; import java.awt.dnd.DragSource; public class DndExample extends

在下面的示例中,有一种触发拖放的标准方法,即mousePress+mouseMove

import javax.swing.*;
import java.awt.datatransfer.StringSelection;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DragGestureListener;
import java.awt.dnd.DragSource;

public class DndExample extends JFrame  {

    public static void main(String[] args) {
        SwingUtilities.invokeLater(() -> new DndExample());
    }

    public DndExample() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JLabel dragLabel = createDndLabel();
        getContentPane().add(dragLabel);
        pack();
        setVisible(true);
    }

    private JLabel createDndLabel() {
        JLabel label = new JLabel("Drag me, please");


        DragGestureListener dragGestureListener = (dragTrigger) -> {
            dragTrigger.startDrag(null, new StringSelection(label.getText()));
        };

        DragSource dragSource = DragSource.getDefaultDragSource();
        dragSource.createDefaultDragGestureRecognizer(label, DnDConstants.ACTION_COPY, dragGestureListener);

        return label;
    }
}

是否可以在没有mouseMove的情况下按下鼠标触发startDrag?所需的行为是这样的:我按下鼠标按钮,然后光标发生变化,指示拖动已经开始,如果移动鼠标,则继续拖动。很明显,我知道我可能会手动添加MouseStener和更改光标,但要恢复以前的光标,需要更多的代码。

因为你要求的是非标准行为,你需要做“额外”的提升自己,这要求你有一个
MouseListener
,其中
mousePressed
设置光标,然后
mouseRelease
使其静止(因此,如果用户只需单击而不拖动组件,你不会得到一个愚蠢的光标状态),并且
DragGestureListener\dragDropEnd
也会重置光标

导入java.awt.Color;
导入java.awt.Cursor;
导入java.awt.Dimension;
导入java.awt.EventQueue;
导入java.awt.Graphics;
导入java.awt.Graphics2D;
导入java.awt.GridBagLayout;
导入java.awt.GridLayout;
导入java.awt.Point;
导入java.awt.datatransfer.DataFlavor;
导入java.awt.datatransfer.transfer;
导入java.awt.datatransfer.UnsupportedFlavorException;
导入java.awt.dnd.DnDConstants;
导入java.awt.dnd.DragGestureEvent;
导入java.awt.dnd.DragGestureListener;
导入java.awt.dnd.DragSource;
导入java.awt.dnd.DragSourceDragEvent;
导入java.awt.dnd.DragSourceDropEvent;
导入java.awt.dnd.DragSourceEvent;
导入java.awt.dnd.DragSourceListener;
导入java.awt.dnd.DropTarget;
导入java.awt.dnd.dropTargetDrageEvent;
导入java.awt.dnd.DropTargetDropEvent;
导入java.awt.dnd.DropTargetEvent;
导入java.awt.dnd.DropTargetListener;
导入java.awt.event.MouseAdapter;
导入java.awt.event.MouseEvent;
导入java.io.IOException;
导入java.util.ArrayList;
导入java.util.List;
导入javax.swing.JFrame;
导入javax.swing.JLabel;
导入javax.swing.JPanel;
导入javax.swing.UIManager;
导入javax.swing.UnsupportedLookAndFeelException;
导入javax.swing.border.LineBorder;
导入javax.swing.border.MatteBorder;
公共类DragAndDropTest{
公共静态void main(字符串[]args){
新DragAndDropTest();
}
公共DragAndDropTest(){
invokeLater(新的Runnable(){
@凌驾
公开募捐{
试一试{
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
}catch(ClassNotFoundException |实例化Exception | IllegalacessException |不支持ookandfeelException ex){
例如printStackTrace();
}
JFrame=新JFrame(“测试”);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(newtestpane());
frame.pack();
frame.setLocationRelativeTo(空);
frame.setVisible(true);
}
});
}
公共类TestPane扩展了JPanel{
公共测试窗格(){
setLayout(新的GridLayout(1,2));
添加(新的DropPane());
添加(新的DragPane());
}
@凌驾
公共维度getPreferredSize(){
返回新维度(200200);
}
}
公共类DragPane扩展了JPanel{
私有DragSource ds;
私人可转让;
公共拖缆机(){
addMouseListener(新的MouseAdapter(){
@凌驾
公共无效鼠标按下(MouseEvent e){
setCursor(Cursor.getPredefinedCursor(Cursor.HAND_Cursor));
}
@凌驾
公共无效MouseEvent(MouseEvent e){
setCursor(Cursor.getDefaultCursor());
}
});
ds=新的DragSource();
可转让=新的可转让(){
@凌驾
公共DataFlavor[]getTransferDataFlavors(){
返回新的DataFlavor[]{DataFlavor.stringFlavor};
}
@凌驾
支持公共布尔值IsDataFlavor(DataFlavor){
返回DataFlavor.stringFlavor.equals(flavor);
}
@凌驾
公共对象getTransferData(DataFlavor flavor)引发不受支持的LavorException、IOException{
返回“这是一个测试”;
}
};
ds.CreateDefaultDragestureRecogniter(此,DnDConstants.ACTION\u COPY\u或\u MOVE,new DragestureListener(){
@凌驾
公共无效DragestureRecognited(DragestureEvent dge){
//这是导出所需数据的地方
//调动
ds.startDrag(dge,Cursor.getPredefinedCursor(Cursor.HAND_Cursor),可转移,新DragSourceListener(){
@凌驾
公共无效dragEnter(DragSourceDragEvent dsde){
}
@凌驾
公共无效dragOver(DragSourceDragEvent dsde){
}
@凌驾
公共作废dropActionChanged(DragSourceDragEvent dsde){
}
@凌驾
公共无效dragExit(DragSourceEvent dse){
}
@凌驾
公共无效dragDropEnd(DragSourceDropEvent dsde){
setCursor(Cursor.getDefaultCursor());
}
});
}
});
setLayout(新的GridBagLayout());
添加(新)
import java.awt.Color;
import java.awt.Cursor;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GridBagLayout;
import java.awt.GridLayout;
import java.awt.Point;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DragGestureEvent;
import java.awt.dnd.DragGestureListener;
import java.awt.dnd.DragSource;
import java.awt.dnd.DragSourceDragEvent;
import java.awt.dnd.DragSourceDropEvent;
import java.awt.dnd.DragSourceEvent;
import java.awt.dnd.DragSourceListener;
import java.awt.dnd.DropTarget;
import java.awt.dnd.DropTargetDragEvent;
import java.awt.dnd.DropTargetDropEvent;
import java.awt.dnd.DropTargetEvent;
import java.awt.dnd.DropTargetListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.LineBorder;
import javax.swing.border.MatteBorder;

public class DragAndDropTest {

    public static void main(String[] args) {
        new DragAndDropTest();
    }

    public DragAndDropTest() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new TestPane());
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class TestPane extends JPanel {

        public TestPane() {
            setLayout(new GridLayout(1, 2));
            add(new DropPane());
            add(new DragPane());
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

    }

    public class DragPane extends JPanel {

        private DragSource ds;
        private Transferable transferable;

        public DragPane() {
            addMouseListener(new MouseAdapter() {
                @Override
                public void mousePressed(MouseEvent e) {
                    setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
                }

                @Override
                public void mouseReleased(MouseEvent e) {
                    setCursor(Cursor.getDefaultCursor());
                }
            });
            ds = new DragSource();
            transferable = new Transferable() {

                @Override
                public DataFlavor[] getTransferDataFlavors() {
                    return new DataFlavor[]{DataFlavor.stringFlavor};
                }

                @Override
                public boolean isDataFlavorSupported(DataFlavor flavor) {
                    return DataFlavor.stringFlavor.equals(flavor);
                }

                @Override
                public Object getTransferData(DataFlavor flavor) throws UnsupportedFlavorException, IOException {
                    return "This is a test";
                }
            };
            ds.createDefaultDragGestureRecognizer(this, DnDConstants.ACTION_COPY_OR_MOVE, new DragGestureListener() {
                @Override
                public void dragGestureRecognized(DragGestureEvent dge) {
                    // This is where you would export the data you want
                    // to transfer
                    ds.startDrag(dge, Cursor.getPredefinedCursor(Cursor.HAND_CURSOR), transferable, new DragSourceListener() {

                        @Override
                        public void dragEnter(DragSourceDragEvent dsde) {
                        }

                        @Override
                        public void dragOver(DragSourceDragEvent dsde) {
                        }

                        @Override
                        public void dropActionChanged(DragSourceDragEvent dsde) {
                        }

                        @Override
                        public void dragExit(DragSourceEvent dse) {
                        }

                        @Override
                        public void dragDropEnd(DragSourceDropEvent dsde) {
                            setCursor(Cursor.getDefaultCursor());
                        }

                    });
                }
            });

            setLayout(new GridBagLayout());
            add(new JLabel("Drag from here"));
            setBorder(new LineBorder(Color.RED));
        }

    }

    public class DropPane extends JPanel {

        private List<Point> dropPoints;

        public DropPane() {
            dropPoints = new ArrayList<>(25);
            setDropTarget(new DropTarget(this, new DropTargetListener() {

                @Override
                public void dragEnter(DropTargetDragEvent dtde) {
                }

                @Override
                public void dragOver(DropTargetDragEvent dtde) {
                }

                @Override
                public void dropActionChanged(DropTargetDragEvent dtde) {
                }

                @Override
                public void dragExit(DropTargetEvent dte) {
                }

                @Override
                public void drop(DropTargetDropEvent dtde) {
                    // Normally here, I'd inspect the Transferable and make sure
                    // what is been dropped and can be imported, I'd then go through
                    // the process of unwrapping the data from the Transferable and 
                    // processing it appropriatly, but in this example, I really don't
                    // care, I just care about WHERE the event occured
                    dropPoints.add(dtde.getLocation());
                    dtde.dropComplete(true);
                    repaint();
                }
            }));
            setLayout(new GridBagLayout());
            add(new JLabel("Drop to here"));
            setBorder(new MatteBorder(1, 1, 1, 0, Color.RED));
        }

        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
            g.setColor(Color.RED);
            for (Point p : dropPoints) {
                g.fillOval(p.x - 2, p.y - 2, 5, 5);
            }
        }

    }

}