首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >无法将COM对象强制转换为Microsoft.Vbe.Interop.VBE

无法将COM对象强制转换为Microsoft.Vbe.Interop.VBE
EN

Stack Overflow用户
提问于 2015-03-27 06:01:28
回答 1查看 702关注 0票数 3

我有一个用C#编写的COM外接程序,它在Microsoft中运行得很好。

有一个GitHub问题询问外接程序是否支持VB6 IDE。;为了使它与VisualStudio6.0一起工作,我需要做什么不同的事情吗?

下面是相关的类列表:

代码语言:javascript
复制
using System;
using Extensibility;
using Microsoft.Vbe.Interop;
using System.Runtime.InteropServices;
using System.ComponentModel;
using System.Windows.Forms;

namespace Rubberduck
{
    [ComVisible(true)]
    [Guid(ClassId)]
    [ProgId(ProgId)]
    [EditorBrowsable(EditorBrowsableState.Never)]
    //underscores make classes invisible to VB6 object explorer
    //Nothing breaks because we declare a ProgId
    public class _Extension : IDTExtensibility2, IDisposable
    {
        public const string ClassId = "8D052AD8-BBD2-4C59-8DEC-F697CA1F8A66";
        public const string ProgId = "Rubberduck.Extension";

        private App _app;

        public void OnAddInsUpdate(ref Array custom)
        {
        }

        public void OnBeginShutdown(ref Array custom)
        {
        }

        public void OnConnection(object Application, ext_ConnectMode ConnectMode, object AddInInst, ref Array custom)
        {
            try
            {
                // these casts fail when host is VB6 environment
                _app = new App((VBE)Application, (AddIn)AddInInst);
            }
            catch (Exception exception)
            {
                MessageBox.Show(exception.Message, "Rubberduck Add-In could not be loaded", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }

        public void OnStartupComplete(ref Array custom)
        {
            if (_app != null)
            {
                _app.CreateExtUi();
            }
        }

        public void OnDisconnection(ext_DisconnectMode RemoveMode, ref Array custom)
        {
            Dispose();
        }

        public void Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }

        protected virtual void Dispose(bool disposing)
        {
            if (disposing & _app != null)
            {
                _app.Dispose();
            }
        }
    }
}

VBEAddIn类型的转换很简单。程序集已注册,并在Office中完全按照预期工作。

我很难找到关于扩展VB6的文档,但我的理解是,所涉及的接口是相同的--通过附加到VB6进程、在强制转换之前中断以及检查Application对象,我可以看到我希望在那里看到的所有成员。

那为什么不起作用呢?以下是项目文件中的相关参考资料:

代码语言:javascript
复制
<Reference Include="extensibility, Version=7.0.3300.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
  <EmbedInteropTypes>True</EmbedInteropTypes>
</Reference>

..。

代码语言:javascript
复制
<COMReference Include="VBIDE">
  <Guid>{0002E157-0000-0000-C000-000000000046}</Guid>
  <VersionMajor>5</VersionMajor>
  <VersionMinor>3</VersionMinor>
  <Lcid>0</Lcid>
  <WrapperTool>primary</WrapperTool>
  <Isolated>False</Isolated>
  <EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2016-09-04 23:47:03

问题是VBA有自己的VBIDE类型库,VB6也有自己的VBIDE类型库。这两个类型库非常相似(尽管VB6版本更丰富),并且都公开了IDTExtensibility2接口。此外,随着IDTExtensibility2是在VB6和Office2000的VBA6.x中引入的,也有用于VB5的VBIDE版本,我猜想,对于Office97的VBA5.x,还有一些版本公开了原始的IDTExtensibility

与Hans的回答相反,外接程序不是Office外接程序,而是一个VBE外接程序,因此它可以在任何支持VBA 6/7 (Office、AutoCAD、CorelDraw、SolidWorks等)的主机上工作。而且它绝对可以在VB6中工作.只是需要多做一点工作。

如果您希望支持VB6 (或VB5,或VBA5.x),则需要添加对相关互操作程序集的引用,并且在连接时需要转换为适当的类型。

我发布了一个关于CodeReview概念的证明,它支持VB6和VBA6.x\7.x。它还远不是一个完整的实现,但是您将看到我创建了一个IVBE接口来抽象不同的VBIDE实现。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/29294260

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档