問題描述
最近我解決了當 DnD 項目從 JList 到 JTable 對象時得到的神秘"IOException.顯然,我傳輸的對象必須是可序列化的.這是必須",還是有辦法避免序列化?
Recently I solved a "mysterious" IOException that I got while DnD items from a JList to the JTable objects. Apparently objects that I transfer must be serializable. Is this "a must", or there is a way to avoid serialization?
我必須注意的一件事 - 我要轉移的類型在不同的包中.
One thing I must note - the type I am transferring is in a different package.
推薦答案
你可以寫一個自定義的TransferHandler.例如,我相信 JTabel 的 TranferHandler 將導出一個以逗號分隔的字符串,然后導入將解析該字符串以將每個標記添加為不同的列.
You can write a custom TransferHandler. For example I believe a TranferHandler for a JTabel will export a String that is comma delimited and then the import will parse the string to add each token as a different column.
因此,在您的情況下,您可以以相同的方式導出數據.然后在您導入時,您需要能夠使用已解析的標記重新創建您的自定義對象.
So in your case you could export you data the same way. Then on you import you would need to be able to recreate your custom Object using the parsed tokens.
查看 拖放和數據傳輸上的 Swing 教程 了解更多信息和示例.
Take a look at the Swing tutorial on Drag and Drop and Data Transfer for more information and examples.
或者,如果 DnD 僅在您的 Java 應用程序之間,則可能比您傳遞對對象的實際引用更容易.這是我嘗試通過在面板之間拖動 Swing 組件來執行此類操作的示例:
Or maybe easier if the DnD is only between your Java application than you can pass the actual reference to the object. Here is an example of my attempt to do something like this by dragging a Swing component between panels:
import java.awt.*;
import java.awt.datatransfer.*;
import java.awt.event.*;
import java.beans.*;
import javax.swing.*;
import javax.swing.border.*;
import javax.swing.plaf.*;
import javax.swing.text.*;
import java.io.*;
public class DragComponent extends JPanel
{
// public final static DataFlavor COMPONENT_FLAVOR = new DataFlavor(Component[].class, "Component Array");
public static DataFlavor COMPONENT_FLAVOR;
public DragComponent()
{
try
{
COMPONENT_FLAVOR = new DataFlavor(DataFlavor.javaJVMLocalObjectMimeType + ";class="" + Component[].class.getName() + """);
}
catch(Exception e)
{
System.out.println(e);
}
setLayout(null);
setTransferHandler( new PanelHandler() );
MouseListener listener = new MouseAdapter()
{
@Override
public void mousePressed(MouseEvent e)
{
JComponent c = (JComponent) e.getSource();
TransferHandler handler = c.getTransferHandler();
handler.exportAsDrag(c, e, TransferHandler.MOVE);
}
};
TransferHandler handler = new ComponentHandler();
for (int i = 0; i < 5; i++)
{
JLabel label = new JLabel("Label " + i);
label.setSize( label.getPreferredSize() );
label.setLocation(30 * (i+1), 30 * (i+1));
label.addMouseListener( listener );
label.setTransferHandler( handler );
add( label );
}
}
private static void createAndShowUI()
{
DragComponent north = new DragComponent();
north.setBackground(Color.RED);
north.setPreferredSize( new Dimension(200, 200) );
DragComponent south = new DragComponent();
south.setBackground(Color.YELLOW);
south.setPreferredSize( new Dimension(200, 200) );
JFrame frame = new JFrame("DragComponent");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(north, BorderLayout.NORTH);
frame.add(south, BorderLayout.SOUTH);
frame.pack();
frame.setLocationByPlatform( true );
frame.setVisible( true );
}
public static void main(String[] args)
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowUI();
}
});
}
}
class ComponentHandler extends TransferHandler
{
@Override
public int getSourceActions(JComponent c)
{
return MOVE;
}
@Override
public Transferable createTransferable(final JComponent c)
{
return new Transferable()
{
@Override
public Object getTransferData(DataFlavor flavor)
{
Component[] components = new Component[1];
components[0] = c;
return components;
}
@Override
public DataFlavor[] getTransferDataFlavors()
{
DataFlavor[] flavors = new DataFlavor[1];
flavors[0] = DragComponent.COMPONENT_FLAVOR;
return flavors;
}
@Override
public boolean isDataFlavorSupported(DataFlavor flavor)
{
return flavor.equals(DragComponent.COMPONENT_FLAVOR);
}
};
}
@Override
public void exportDone(JComponent c, Transferable t, int action)
{
System.out.println(c.getBounds());
}
}
class PanelHandler extends TransferHandler
{
@Override
public boolean canImport(TransferSupport support)
{
if (!support.isDrop())
{
return false;
}
boolean canImport = support.isDataFlavorSupported(DragComponent.COMPONENT_FLAVOR);
return canImport;
}
@Override
public boolean importData(TransferSupport support)
{
if (!canImport(support))
{
return false;
}
Component[] components;
try
{
components = (Component[])support.getTransferable().getTransferData(DragComponent.COMPONENT_FLAVOR);
}
catch (Exception e)
{
e.printStackTrace();
return false;
}
Component component = components[0];
Container container = (Container)support.getComponent();
container.add(component);
// container.revalidate();
// container.repaint();
container.getParent().revalidate();
container.getParent().repaint();
JLabel label = (JLabel)component;
DropLocation location = support.getDropLocation();
System.out.println(label.getText() + " + " + location.getDropPoint());
label.setLocation( location.getDropPoint() );
return true;
}
}
這篇關于可以避免在同一應用程序中的 JComponent 之間的 DnD 中進行序列化嗎?的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網!