一、问题描述:做IDE开发经常会遇到这样一种情况:使用者开两个应用程序,把一个应用程序中的控件copy到另一个应用程序中。
这样做只是用户的一个使用小细节便于使用者对比刻制,我们如果能抓住这些细节,那么我们的产品客户体验度会上一个层次。
二、解决思路:跨应用程序copy,也可以说是两个单独的进程间通信。两个进程间的通信大概有以下几种:剪贴板Clipboard、窗
口消息、使用共享内存、动态数据交换、消息管道(有匿名通道、命名通道)、邮件槽、套接字、internet、RPC(远程过程调用)、串
行并行通信、COM/DCOM等。当前采用剪切板的方式。
原理如下:在copy端,把要copy的数据写到剪切板中,在pase端,在剪切板中取出对应类型的数据。
三、解决方案:开始以为:按照上面说的原理,把控件写到剪切板中不就ok。范例如下:
copy端:
TreeNode t = new TreeNode("ClipBoardNode");
Clipboard.SetData("TreeNode", t); pase端: TreeNode t = (TreeNode)Clipboard.GetData("TreeNode"); if (treeView1.SelectedNode == null) treeView1.Nodes.Add(t); else treeView1.SelectedNode.Nodes.Add(t); 可是一运行出现当机:error信息大致是:TreeNode 不可以序列化。 原来:对于控件是不可以直接写到剪切板中的,写到剪切板中的数据必须是以流的形式。而上面,控件是不可以直接序列化成流的。 新的解决方案: 需要写个单独的方法,对控件做序列化处理后,才能写到剪切板中。 private string Serialize(object objectToSerialize) { string serialString = null; using (System.IO.MemoryStream ms1 = new System.IO.MemoryStream()) { BinaryFormatter b = new BinaryFormatter(); b.Serialize(ms1, objectToSerialize); byte[] arrayByte = ms1.ToArray(); serialString = Convert.ToBase64String(arrayByte); } return serialString; } private object DeSerialize(string serializationString) { object deserialObject = null; byte[] arrayByte = Convert.FromBase64String(serializationString); using (System.IO.MemoryStream ms1 = new System.IO.MemoryStream(arrayByte)) { BinaryFormatter b = new BinaryFormatter(); deserialObject = b.Deserialize(ms1); } return deserialObject; } 然后:copy端: TreeNode t = new TreeNode("ClipBoardNode"); Clipboard.SetData("TreeNode", Serialize(t)); pase端: TreeNode t = (TreeNode)DeSerialize(Clipboard.GetData("TreeNode").ToString()); if (treeView1.SelectedNode == null) treeView1.Nodes.Add(t); else treeView1.SelectedNode.Nodes.Add(t);