46

我想知道在我的 C++ 应用程序中注册文件扩展名的最简洁方法,以便在双击与我的程序关联的数据文件时,打开应用程序并将文件名作为参数传递给应用程序。

目前,我通过我的 wix 安装程序执行此操作,但在某些情况下应用程序不会安装在用户的计算机上,因此我还需要通过应用程序创建注册表项的选项。

此外,这是否也意味着如果应用程序被删除,注册表中未使用的条目将被遗留下来?

4

4 回答 4

88

您可以在此 MSDN 文章中找到对该过程的基本概述。关键部分位于列表的底部:

  • 注册 ProgID

ProgID(本质上是文件类型注册表项)包含重要的文件类型属性,例如图标、描述和上下文菜单项,包括双击文件时使用的应用程序。许多扩展名可能具有相同的文件类型。该映射在下一步中完成:

  • 注册文件类型的文件扩展名

在这里,您为扩展设置了一个注册表值,将该扩展的文件类型设置为您在上一步中创建的 ProgID。

使用应用程序打开文件所需的最少工作量是设置/创建两个注册表项。在这个示例.reg文件中,我创建了一个文件类型 ( blergcorp.blergapp.v1) 并将一个文件扩展名 ( .blerg) 与其关联。

Windows Registry Editor Version 5.00

[HKEY_CURRENT_USER\Software\Classes\blergcorp.blergapp.v1\shell\open\command]
@="c:\path\to\app.exe \"%1\""
[HKEY_CURRENT_USER\Software\Classes\.blerg]
@="blergcorp.blergapp.v1"

现在,您可能希望以编程方式完成此操作。为了绝对的犹太教,你可以检查这些键的存在,并相应地改变你的程序行为,特别是如果你假设控制一些常见的文件扩展名。但是,可以通过使用 SetValue 函数设置这两个键来实现目标。

我不赞成确切的 C++ 语法,但在 C# 中,语法看起来像这样:

Registry.SetValue(@"HKEY_CURRENT_USER\Software\Classes\blergcorp.blergapp.v1\shell\open\command", null, @"c:\path\to\app.exe \"%1\"");
Registry.SetValue(@"HKEY_CURRENT_USER\Software\Classes\.blerg", null, "blergcorp.blergapp.v1");

当然你可以手动打开每个子键,手动创建 ProgID 和扩展子键,然后设置键值,但是这个SetValue功能的一个好处是如果键或值不存在,它们会自动创建。非常便利。

现在,简要介绍一下使用哪个蜂巢。许多在线文件关联示例,包括 MSDN 上的示例,都显示这些键设置在HKEY_CLASSES_ROOT. 我不建议这样做。该配置单元是HKEY_LOCAL_MACHINE\Software\Classes(系统默认值)和HKEY_CURRENT_USER\Software\Classes(每个用户设置)的合并虚拟视图,并且对配置单元中的任何子键的写入都被重定向到HKEY_LOCAL_MACHINE\Software\Classes. 现在,这样做没有直接问题,但您可能会遇到这个问题:如果您写入 HKCR(重定向到 HKLM),并且用户在 HKCU 中指定了具有不同值的相同键,则 HKCU 值将优先。因此,您的写入将成功,但您不会看到任何更改,因为HKEY_CURRENT_USER设置优先于HKEY_LOCAL_MACHINE设置。

因此,在设计应用程序时应考虑到这一点。现在,另一方面,您可以只写信给HKEY_CURRENT_USER,正如我在此处的示例所示。但是,该文件关联设置只会为当前用户加载,如果您的应用程序已为所有用户安装,则当其他用户在 Windows 中打开文件时,您的应用程序将不会启动。

对于您想做的事情,这应该是一本不错的入门书。为了进一步阅读,我建议

另请参阅我对类似问题的类似回答:

于 2010-01-15T04:39:06.943 回答
8

这是一个两步过程:

1.定义一个程序来处理扩展:(除非你想使用现有的)
      1.1 例如在“HKCU\\Software\\Classes\\”中创建一个key
          “软件\\类\\你的程序名.file.ext”
      1.2 创建子项“Software\\Classes\\YourProgramName.file.ext\\DefaultIcon”
        1.2.1 将默认值(“”)设置为您的应用程序完整路径以获取
              资源中的图标
      1.3 创建子键“Software\\Classes\\YourProgramName.file.ext\\Shell\\OperationName\\Command”
          OperationName = 例如打开、打印或其他
        1.3.1 将默认值(“”)设置为您的应用程序完整路径+可选运行时参数(文件名)

2.将文件扩展名与程序相关联。
  2.1 创建一个密钥 HKCU\\Software\\Classes\\.ext - 这是你的扩展
  2.2 给程序定义键设置默认值
    (“你的程序名.file.ext”)

下面是用 c# 编写的关联文件扩展名的程序的一部分。它不是 c++,但我认为解释自己和 AFAIK 很简单,如果与 c++ 中的代码不完全相同的话

1.


    RegistryKey keyPFCTExt0 = Registry.CurrentUser.OpenSubKey("Software\\Classes\\PFCT.file.enc", true);
        if (keyPFCTExt0 == null)
        {
            keyPFCTExt0 = Registry.CurrentUser.CreateSubKey("Software\\Classes\\PFCT.file.enc");
            keyPFCTExt0.CreateSubKey("DefaultIcon");
                RegistryKey keyPFCTExt0ext = Registry.CurrentUser.OpenSubKey("Software\\Classes\\PFCT.file.enc\\DefaultIcon", true);
                    keyPFCTExt0ext.SetValue("", Application.ExecutablePath +",0");
                keyPFCTExt0ext.Close();
            keyPFCTExt0.CreateSubKey("Shell\\PFCT_Decrypt\\Command");
        }
    keyPFCTExt0.SetValue("", "PFCT.file.enc");
    keyPFCTExt0.Close();

2.


    RegistryKey keyPFCTExt1 = Registry.CurrentUser.OpenSubKey("Software\\Classes\\PFCT.file.enc\\Shell\\PFCT_Decrypt\\Command", true);
        if (keyPFCTExt1 == null)
            keyPFCTExt1 = Registry.CurrentUser.CreateSubKey("Software\\Classes\\PFCT.file.enc\\Shell\\PFCT_Decrypt\\Command");
        keyPFCTExt1.SetValue("", Application.ExecutablePath + " !d %1"); //!d %1 are optional params, here !d string and full file path
        keyPFCTExt1.Close(); 

于 2009-09-09T20:30:20.253 回答
8

我不知道为什么人们一直说这HKEY_CURRENT_USER\Software\Classes\<.ext>是默认值(这会将您重定向到另一个(软件创建的)类。

它确实有效,但它会被覆盖

HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Explorer\FileExts\<.ext>\UserChoice

而且我相信微软推荐第二种做法——因为这是内置的“打开方式”正在做的事情。在这种情况下,Progid" key 的值等于默认值 of 。HKEY_CURRENT_USER\Software\Classes\<.ext>

于 2014-08-19T17:35:27.057 回答
0

我在尝试使用 C# 操作关联时发现了以下内容:

  • hkcu\software\microsoft\windows\currentVersion\explorer\fileexts.reg\userchoice -> 用于用户特定设置。openWithProgIds 键中的值指向 hkcr 中的键。
  • hkcr\xfile\shell\open\muiVerb 值或 hkcr\xfile\shell\open\command\default 值 -> 影响打开处理程序。这是包含程序路径的值。
  • hkcr\ .x -> 影响上下文菜单(新 x)以及与菜单相关的其他内容。

我不知道 C++ 代码,但鉴于这些信息,您必须能够使用注册表 API 操作注册表。

于 2019-04-30T10:56:38.977 回答