如何检测剪贴板中的数据是用于复制还是移动?


我可以从剪贴板获取文件列表,但我无法检测该数据是用于移动还是复制?

当用户单击“剪切”和“粘贴”选项时,数据被设置到剪贴板中,我们可以使用一些代码检索它,但我们如何同时获取此剪贴板数据是用于复制还是剪切?

我尝试过的:

我可以使用以下代码从剪贴板获取文件列表:
IDataObject 数据 = Clipboard.GetDataObject();
if (!data.GetDataPresent(DataFormats.FileDrop))
返回;
细绳[] 剪贴板数据=(字符串[])data.GetData(DataFormats.FileDrop);

解决方案5

C#
[Flags]
public enum NativeDropEffect : uint
{
    None = 0x00000000,
    Copy = 0x00000001,
    Move = 0x00000002,
    Link = 0x00000004,
    Scroll = 0x80000000
}

IDataObject iData = System.Windows.Forms.Clipboard.GetDataObject();
var fileDrop = (string[])iData.GetData(DataFormats.FileDrop);
NativeDropEffect dropEffect;
using (var reader = new BinaryReader((MemoryStream)iData.GetData("Preferred DropEffect")))
{
    dropEffect = (NativeDropEffect)reader.ReadUInt32();
}

if(dropEffect.HasFlag(NativeDropEffect.Copy))
{
//copy
}
else if(dropEffect.HasFlag(NativeDropEffect.Move))
{
//cut
}

复制文件时,它似乎设置了复制和链接标志,而对于剪切,它设置了移动位标志。

解决方案3

决不。 而且你永远不需要它。 首先,不存在这样的区别。 这个问题根本没有意义。

我还要解释一下:不存在“剪贴板移动”这样的东西。 这是纯粹的应用程序端部分。 你只是错过了这个想法。 是的,有些应用程序提供了“剪切文件——过去文件”操作,其功能相当于“移动”,但这只是一个比喻。 在操作系统中,没有这样的东西。

一个例子是“移动文件”。 它的工作原理如下:首先,应用程序处理“剪切文件”命令并简单地标记一些计划移动的文件。 重要的是要明白没有任何内容被削减。 下一个命令应该是“粘贴文件”。 如果它在任何其他剪贴板操作之前发出,则文件将被简单地移动。 如果用户执行其他操作,“剪切”命令将被忽略; 并且文件保留在原来的位置。 如果用户发出该命令,文件就会被移动。 电子表格(包括 Excel)的单元格也会发生同样的情况。

您可以在您的应用程序中开发相同的技术。 问题是:系统剪贴板是否参与其中? 答案是:是又不是。 正如上一段中解释的两个示例一样,您的应用程序可以在应用程序进程的多个实例的一个实例中执行。 如果一直都是 同一实例,使用剪贴板是没有意义的。 但同一个应用程序可以在多个不同的进程中执行; 并且进程是隔离的。 他们需要就该文件复制/粘贴/移动活动进行沟通; 这可以通过可用的系统剪贴板方便地完成。 实现类似的事情所需要做的就是很少的逻辑推理。

此外,对于文件操作:您可以使用 Shell API 拥有多个不相关的应用程序。 它们不仅是不同的进程,甚至是不同应用程序的进程。 在这方面,他们可以通过系统剪贴板进行通信。

就这样。

-SA

解决方案1

这对于剪贴板来说是不可能的,它是由使用剪贴板的应用程序决定的。 对不起 !

解决方案2

当您使用文件拖放时,只需检查 Shift 和 Control 键:

C#
if ((ModifierKeys & Keys.Shift) != 0)
    {
    // It's a move operation.
    ...
    }

コメント

タイトルとURLをコピーしました