创建一个基本的、非托管的 Outlook/Office 插件

Posted

技术标签:

【中文标题】创建一个基本的、非托管的 Outlook/Office 插件【英文标题】:Creating a Bare Bones, Unmanaged Outlook/Office Addin 【发布时间】:2016-06-17 11:03:51 【问题描述】:

2016 年 3 月 3 日

我想使用 C++ 为 Microsoft Outlook/Office 编写一个纯粹的、基本的、非托管的 COM 插件。 Visual Studio 强制您使用活动模板库并隐藏主机 (Outlook) 如何连接到插件的所有基本实现。以下是我目前所知道的一些背景:

    我了解 COM 的基本原理及其工作原理。根据我对架构的理解,我得出的结论是,既然 Outlook 是在 COM 之上编写的,那么我当然应该能够查询它的接口并操作应用程序。

    我知道我需要使用 IDTExtensibility2 接口来连接办公应用程序。有谁知道这个接口的定义所在的头文件的名称吗?

    我知道我需要在注册表中注册插件。这是一个 COM 服务器,所以这是意料之中的。

除了这些点,我迷路了。我需要知道第 1 步。任何人都可以提供任何类型的参考或一些代码吗?

为了记录,我不想使用 VS,因为我想知道如何从头开始创建插件。我想知道需要哪些组件,而不是包中提供的组件。

编辑 3/4/16

所以我偶然发现了 MSDN 上的这个链接:

https://msdn.microsoft.com/en-us/library/office/ff867268.aspx

我不知道我是怎么错过的,但它看起来是一个很好的起点。我想我唯一的挂断是使用什么标题。这可能是一次冒险,我必须冒险找出裸骨插件需要哪些。我会做一些研究并向这个帖子报告。

【问题讨论】:

【参考方案1】:
    是的。 请参阅_IDTExtensibility2, what DLL to import into ATL project? 了解 IDTExtensibility2 接口定义 是的。请记住,有一些 Outlook 特定的键可以让 Outlook 在 HKEY_CURRENT_USER\Software\Microsoft\Office\Outlook\Addins 中加载您的插件

这里是 IDTExtensibility2 接口的 Delphi 定义: // *********************************************************************// // Interface: _IDTExtensibility2 // Flags: (4432) Hidden Dual OleAutomation Dispatchable // GUID: B65AD801-ABAF-11D0-BB8B-00A0C90F2744 // *********************************************************************// _IDTExtensibility2 = interface(IDispatch) ['B65AD801-ABAF-11D0-BB8B-00A0C90F2744'] procedure OnConnection(const Application: IDispatch; ConnectMode: ext_ConnectMode; const AddInInst: IDispatch; var custom: PSafeArray); safecall; procedure OnDisconnection(RemoveMode: ext_DisconnectMode; var custom: PSafeArray); safecall; procedure OnAddInsUpdate(var custom: PSafeArray); safecall; procedure OnStartupComplete(var custom: PSafeArray); safecall; procedure OnBeginShutdown(var custom: PSafeArray); safecall; end;

【讨论】:

好吧,我假设 _IDTExtensibility2 是在 MSADNSDR.dll 中实现的,我假设这是要导入的主要 dll。是否有任何其他必须从中导入的基线 dll?是否应该将 Outlook 应用程序传递给 _IDTExtensibility2::OnConnection?如果是这样,如何通过? MSADNSDR.dll 没有实现 _IDTExtensibility2 接口。它在作为资源嵌入的类型库中定义它。没有什么可以阻止您在代码中硬编码 _IDTExtensibility2 接口定义。您不会将 Application 对象传递给 IDTExtensibility2::OnConnection 方法,Outlook 会在调用您的实现时为您执行此操作。该参数被声明为通用 IDispatch。您可以使用后期绑定来访问它,也可以从 MSOUTL.OLB 文件中导入 Outlook 类型库定义。 你有书面的例子可以分享吗?我真的很感激。我只会将其用于教育目的。 不,我用的是 Delphi,对不起。 顺便感谢您的快速和有益的回复。你是英雄。我会举一个德尔福的例子。 COM 是独立于语言的,所以我相信它会相关。

以上是关于创建一个基本的、非托管的 Outlook/Office 插件的主要内容,如果未能解决你的问题,请参考以下文章

.NET对象与Windows句柄:句柄的基本概念

42.从非托管磁盘创建虚拟机

通过非托管自定义镜像创建VM

桥接非托管类和托管类

反向 PInvoke 并创建一个完整的非托管 C# 程序

为非托管 C++ 客户端创建 WCF 服务