0

描述我的问题有点棘手,但我会尽力而为。

首先,我正在使用 C 和 WinAPI 开发一个多文档界面应用程序。我的程序能够解析命令行参数以打开多个文件。我把这个字符串: “X:\MyAppName.exe”“%1” 放在 txt 文件的打开命令列表下,这样现在我可以右键单击 Windows 资源管理器中的任何 .txt 文件并使用我的应用程序打开它。但是,当我选择多个文件时,资源管理器会多次运行命令“X:\MyAppName.exe”“%1”,以便启动我的应用程序的多个实例。

可是等等! 这还不是最棘手的部分。相反,我的应用程序将打开单个文件和一次打开多个文件视为具有不同视觉样式的两个不同事物。我知道一次保持一个实例运行的想法(尽管我不知道实现它的 C 代码)。但是我不知道如何区分一个一个打开多个文件和同时打开多个文件。

我希望我说清楚。

4

1 回答 1

1

像现在这样使用注册表,您将无法直接区分多个文件和单个文件。正如您已经注意到的,每个请求的文件都会启动您的应用程序的新副本。如果您实现单实例化(这并不难),您可以做的是检测何时请求第一个文件并启动一个短计时器,然后让每个后续文件重置该计时器。当它最终过去时,检查您收集了多少文件并根据需要对它们采取行动。

一个更好的首选解决方案是在您的应用程序中创建一个进程外 COM 对象来实现该IDropTarget接口。然后,Windows 将能够通过单个入口点将文件信息汇集到您的应用程序中。您的应用不必关心信息的来源。您一次不仅可以支持多个文件,还可以支持不同格式的文件信息(Windows 可以只向您传递文件名,或者它可以向您传递实际的文件数据本身)。

Windows 将构造一个IDataObject对象来保存所需的任何文件信息,然后将其传递给您的IDropTarget对象。如果您的应用程序已经在运行,COM 将能够访问您现有的IDropTarget对象。如果您的应用程序尚未运行,COM 将在访问其IDropTarget对象之前自动启动您的应用程序。无论哪种方式,一旦它运行,您IDropTarget可以查看传递给它的任何数据并决定是接受还是拒绝它。

如果您将 COM 对象注册CLSIDDropTarget所需的文件扩展名,用户将能够双击此类文件,或选择此类文件并按 Enter,它们将被传递给您的IDropTarget对象。

If you register an AppPath for your app and then register the CLSID as a DropTarget for it, users will be able to drag files, regardless of extension, onto your app's exe file itself, and they will be passed to your IDropTarget object.

If you use the same COM object with the RegisterDragDrop() function, users will be able to drag files, regardless of extension, onto your app's UI directly, and they will be passed to your IDropTarget object.

于 2012-11-21T00:08:59.790 回答