好的,这个问题超出了我的范围。我正在尝试实现一个GUI小部件,该小部件允许将文件拖放到JTable上,并允许将JTable的行拖动以进行重新排序。考虑一下VLC的播放列表或iTunes中的一个。
我可以从OS(Explorer,Finder等)中删除文件,但工作正常,但是一旦文件放入,我就无法重新安排表的行了。问题是当我添加文件时一个自定义的TransferHandler到表,从表中拖动立即被杀死。这是一些示例代码:
import javax.swing.*;
public class TableTest
{
public static void main (String [] argv)
{
// setup table data
String [] columns = new String [] {"Foo", "Bar", "Baz", "Quux"};
String [][] data = new String [][] {{"A", "B", "C", "D"},
{"1", "2", "3", "4"},
{"i", "ii", "iii", "iv"}};
// create table
JTable table = new JTable(data, columns);
// set up drag and drop
table.setDragEnabled(true);
table.setDropMode(DropMode.INSERT_ROWS);
table.setFillsViewportHeight(true);
TransferHandler dnd = new TransferHandler() {
// here be code to handle drops, and one would
// presume drag exporting, too
};
table.setTransferHandler(dnd);
JScrollPane scroll = new JScrollPane(table);
// create and show window
JFrame window = new JFrame();
window.getContentPane().add(scroll);
window.pack();
window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
window.setVisible(true);
}
}
按原样运行此代码,您将看到无法在表上发起拖动。如果在表上注释掉对setTransferHandler()的调用,则拖动工作有效(例如,当我开始拖动表行时,我得到X'd圆形光标说我不能放到那里)。但是,一旦为表设置了TransferHandler,就无法拖动任何行。问题一定在TransferHandler中,但是我已经对它进行了彻底的故障排除和调试,并确定一旦表上有TransferHandler,就永远不会开始拖动。我究竟做错了什么?
最佳答案
我有同样的问题,它与您的TransferHandler的自定义实现无关。替换TransferHandler时,还需要保留默认的DragSource并告诉它识别拖动手势。您可能还需要实现自己的Transferable,因为您需要将其传递给DragGestureEvent.startDrag()方法。
table.setTransferHandler(new MyTransferHandler());
table.setDragEnabled(true);
DragSource source = DragSource.getDefaultDragSource();
source.createDefaultDragGestureRecognizer(table, DnDConstants.ACTION_COPY, new DragGestureListener() {
@Override
public void dragGestureRecognized(DragGestureEvent dge) {
//grab the selected files from the table model
ArrayList<File> files = new ArrayList<File>();
for (int row : table.getSelectedRows()) {
files.add((File) dm.getValueAt(row, 1));
}
//FileTransferable is a custom Transferable implementation
Transferable transferable = new FileTransferable(files);
//and this is the magic right here
dge.startDrag(null,transferable);
}
});