简体   繁体   中英

Dragging a file from a JList to a Windows Explorer window

First I just want to admit that I'm not the sharpest Java developer out there. My strengths/experiences are mostly in JavaScript, etc. browsers.

I've been asked to create an applet that can be used for dragging/dropping files into the browser (IE7). That was no problem. I used the FileDrop class from here .

So we're about to go live, but the client has decided after showing the application to a pool of users that the application needs to be able to drag files out of the interface and into a Windows Explorer/Desktop, etc. kind of thing.

The way the UI is set up is they have a list of files in a content pane at the right, and a navigation area to the left--a tree of directories, etc. that when the user clicks, they get a list of files in the content area. When the user clicks and holds the mouse down, the applet eventually appears with the file it has downloaded and the user clicks to drag that file out of the interface and into another drop target in the UI or out to a Windows Explorer, etc.

Here is some code from the applet:

public MyFileDrop() {

    panel = new JPanel();
    panel.setLayout(new GridBagLayout());
    panel.setBorder(BorderFactory.createLineBorder(Color.gray, 1));
    panel.setBackground(new Color(245, 245, 245));

    JLabel label = new JLabel("+", JLabel.CENTER);

    label.setFont(new Font(Font.SANS_SERIF, Font.BOLD, 15));
    label.setForeground(Color.gray);
    panel.add(label);

        DefaultListModel model = new DefaultListModel();

        fileList = new JList(model);
        fileList.setDragEnabled(true);

        fileList.setSize(250, 25);
        panel.add(fileList);

    panel.addMouseListener(new MouseAdapter() {

        public void mouseEntered(java.awt.event.MouseEvent evt) {
            System.out.println("mouseEntered");

            File file = self.getAndSaveLocalFile(self.documentUrl, self.name, self.id);

            if (!file.isDirectory())
                ((DefaultListModel) ((JList) panel.getComponent(1)).getModel()).addElement(file);
        }

...

When I drag the file out to the Windows Explorer window, it gives me the circle-slash image (ie, like "no-smoking" without the cigarette). And it doesn't get dropped into the targets on the UI, either. I've sysouted the .getCannonicalPath() of the file, and everything seems to be pointing to the notion that I'm dragging a file out, but the system doesn't seem to recognize that. I've looked at this question:

DragNDrop from Java to Windows Explorer

But I'm using the built-in drag and drop feature of JList, and I don't know how to change the mimetype. Do I need to write my own TransferHandler? If so, what does it need to do exactly?

I ended up copying this code from the best answer to this question: Swing application -> Drag & drop to the desktop / folder

private class FileTransferHandler extends TransferHandler {

    @Override
    protected Transferable createTransferable(JComponent c) {
        JList list = (JList) c;
        List<File> files = new ArrayList<File>();
        for (Object obj: list.getSelectedValues()) {
            files.add((File)obj);
        }
        return new FileTransferable(files);
    }

    @Override
    public int getSourceActions(JComponent c) {
        return MOVE;
    }
}

private class FileTransferable implements Transferable {

    private List<File> files;

    public FileTransferable(List<File> files) {
        this.files = files;
    }

    public DataFlavor[] getTransferDataFlavors() {
        return new DataFlavor[]{DataFlavor.javaFileListFlavor};
    }

    public boolean isDataFlavorSupported(DataFlavor flavor) {
        return flavor.equals(DataFlavor.javaFileListFlavor);
    }

    public Object getTransferData(DataFlavor flavor)
            throws UnsupportedFlavorException, IOException {
        if (!isDataFlavorSupported(flavor)) {
            throw new UnsupportedFlavorException(flavor);
        }
        return files;
    }
}

and then I set the TransferHandler on the JList like this:

DefaultListModel model = new DefaultListModel();
JList fileList = new JList(model);
fileList.setDragEnabled(true);
fileList.setTransferHandler(new FileTransferHandler());

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM