我正在使用Clipboard.GetData
一个类型的对象SerializedClipboardFragment
——这是我自己的一个类型,一个类,我用[Serializable()]
属性标记了它:
[Serializable()]
public class SerializedClipboardFragment
{
readonly string[] m_ancestors;
readonly string m_fragment;
readonly int m_numberOfNodes;
readonly bool m_isInsertingBlock;
readonly bool m_isInsertingTable;
public SerializedClipboardFragment(
string[] ancestors,
string fragment,
int numberOfNodes,
bool isInsertingBlock,
bool isInsertingTable
)
{
m_ancestors = ancestors;
m_fragment = fragment;
m_numberOfNodes = numberOfNodes;
m_isInsertingBlock = isInsertingBlock;
m_isInsertingTable = isInsertingTable;
}
internal static DataFormats.Format s_format;
static SerializedClipboardFragment()
{
s_format = DataFormats.GetFormat(typeof(SerializedClipboardFragment).FullName);
}
... etc -- various get-only properties ...
}
我从剪贴板获取此数据的代码如下所示:
public static SerializedClipboardFragment getSerializedFragment()
{
if (!Clipboard.ContainsData(SerializedClipboardFragment.s_format.Name))
{
return null;
}
object o = Clipboard.GetData(SerializedClipboardFragment.s_format.Name);
return (SerializedClipboardFragment)o;
}
当我测试这个时,我发现它通常有效。
但它有时会在我的自动回归测试中失败,我尝试在设置后立即从剪贴板获取数据......例如,它可能会在 30 次连续成功的 set-then-get 尝试后失败。
如果它失败了,就像你描述的那样,即对象是MemoryStream
.
请注意,它不应该因为Clipboard.ContainsData
最近返回而失败true
。
我意识到只有一个系统剪贴板;运行此测试时,我的手不在键盘上,发生这种情况时我并不想自己干扰剪贴板。
无论如何,如果我编写如下代码,问题似乎就消失了:
public static SerializedClipboardFragment getSerializedFragment()
{
if (!Clipboard.ContainsData(SerializedClipboardFragment.s_format.Name))
{
return null;
}
// sometimes return MemoryStream object instead under automated-testing
// possibly a timing problem
object o = null;
for (int i = 0; i < 10; ++i)
{
o = Clipboard.GetData(SerializedClipboardFragment.s_format.Name);
if (o is SerializedClipboardFragment)
return (SerializedClipboardFragment)o;
System.Threading.Thread.Sleep(100);
}
return (SerializedClipboardFragment)o;
}
因此,除非我弄错了,否则这可能是一些令人反感的计时错误,与在剪贴板中存储自定义数据类型相关。