Office 2013 c# 加载项 - 空工作簿对象 HRESULT:0x800A03EC 错误
Office 2013 c# add-in - Null workbook object HRESULT: 0x800A03EC error
使用 Visual Studio Enterprise 2015 和 office 2013 pro,我创建了一个 Excel 2013 插件,当我调试它时,我无法引用 Application.Workbook 对象!这是一个最小的例子:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using Excel = Microsoft.Office.Interop.Excel;
using Office = Microsoft.Office.Core;
using Microsoft.Office.Tools.Excel;
namespace ExcelAddIn1
{
public partial class ThisAddIn
{
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
var app = Globals.ThisAddIn.Application;
var wb = app.ThisWorkbook;
}
private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
{
}
#region VSTO generated code
private void InternalStartup()
{
this.Startup += new System.EventHandler(ThisAddIn_Startup);
this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
}
#endregion
}
}
在尝试分配 wb 时,我收到错误消息:
"An exception of type 'System.Runtime.InteropServices.COMException' occurred in ExcelAddIn1.dll but was not handled in user code".
在检查(快速观察)应用程序对象时,许多属性具有以下值:
{System.Reflection.TargetInvocationException:调用目标抛出异常。 ---> System.Runtime.InteropServices.COMException: 旧格式或无效类型库。 (HRESULT 异常:0x80028018(TYPE_E_INVDATAREAD))“
应用程序对象似乎没有工作簿,还有其他问题。
我确定代码没问题,但也许我的 .Net 框架或办公版本或构建设置有问题?
任何人都可以对此有所了解吗?
** 编辑 1 **
因此,根据 Richard Morgan 的建议,我尝试了以下操作,发现原始代码运行时可能没有活动工作簿:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using Excel = Microsoft.Office.Interop.Excel;
using Office = Microsoft.Office.Core;
using Microsoft.Office.Tools.Excel;
namespace ExcelAddIn1
{
public partial class ThisAddIn
{
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
this.Application.WorkbookActivate += new Excel.AppEvents_WorkbookActivateEventHandler(WorkWithWorkbook);
}
private void WorkWithWorkbook(Microsoft.Office.Interop.Excel.Workbook workbook)
{
// Workbook has been opened. Do stuff here.
var app = Globals.ThisAddIn.Application;
Excel.Workbook wb = app.ThisWorkbook;
}
private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
{
}
#region VSTO generated code
private void InternalStartup()
{
this.Startup += new System.EventHandler(ThisAddIn_Startup);
this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
}
#endregion
}
}
因此,当执行 WorkWithWorkbook() 时,我希望有一个 ActiveWorkbook 可供参考。不幸的是,我仍然得到 COMException:
"Exception from HRESULT: 0x800A03EC".
进一步检查应用程序对象表明工作簿集合已部分填充,但许多属性仍引用:
System.Runtime.InteropServices.COMException - 旧格式或无效类型库
进一步搜索发现这可能是由于 Excel 和 VS code 之间的区域设置不匹配造成的,但我已经检查过在这种情况下区域是否匹配。
编辑 2
所以也许我在这里很愚蠢!进一步阅读表明,应用程序的 .ThisWorkbook 属性 returns 是对包含代码的工作簿的引用。由于这是一个加载项,因此代码包含在 .dll 中。因此,我使用了 .ActiveWorkbook,它返回了一个引用而没有抛出异常!
由于工作簿中不包含加载项代码,因此未设置 Application.ThisWorkbook
属性。 Application.ThisWorkbook
属性 用于return 对包含代码的工作簿的引用,并且不存在这样的工作簿!
为了获得对当前打开的工作簿的引用并导致代码被执行,应该改用 Application.ActiveWorkbook
引用。
奇怪的代码:
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
this.Application.WorkbookActivate += new Excel.AppEvents_WorkbookActivateEventHandler(WorkWithWorkbook);
}
private void WorkWithWorkbook(Microsoft.Office.Interop.Excel.Workbook workbook)
{
// Workbook has been opened. Do stuff here.
var app = Globals.ThisAddIn.Application;
Excel.Workbook wb = app.ThisWorkbook;
}
因此,Excel 为您提供刚刚激活的确切 Workbook
,然后您 运行 自己编写代码?!
对此要非常小心。
我们的 VSTO Excel 插件中的 ActiveWorkbook
和 ThisWorkbook
有问题,特别是当用户 "do something" 启动我们的 VSTO 代码时,但他们有其他问题Excel 个文件打开,或者我们的 VSTO 任务需要一些时间,同时它们切换到另一个工作簿。
确保代码处理正确文件的最佳(唯一?)方法是始终使用传递给 OnActivate
函数的 Workbook
。
private void WorkWithWorkbook(Microsoft.Office.Interop.Excel.Workbook workbook)
{
// Do some stuff directly with "workbook"
//
}
至于 0x800A03EC 错误,它似乎是 Excel 的通用 "this could mean anything" COM 错误之一。
我们在尝试计算我们应该使用哪个ExcelWorkbook
对象时也看到了它。
使用 Visual Studio Enterprise 2015 和 office 2013 pro,我创建了一个 Excel 2013 插件,当我调试它时,我无法引用 Application.Workbook 对象!这是一个最小的例子:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using Excel = Microsoft.Office.Interop.Excel;
using Office = Microsoft.Office.Core;
using Microsoft.Office.Tools.Excel;
namespace ExcelAddIn1
{
public partial class ThisAddIn
{
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
var app = Globals.ThisAddIn.Application;
var wb = app.ThisWorkbook;
}
private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
{
}
#region VSTO generated code
private void InternalStartup()
{
this.Startup += new System.EventHandler(ThisAddIn_Startup);
this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
}
#endregion
}
}
在尝试分配 wb 时,我收到错误消息:
"An exception of type 'System.Runtime.InteropServices.COMException' occurred in ExcelAddIn1.dll but was not handled in user code".
在检查(快速观察)应用程序对象时,许多属性具有以下值:
{System.Reflection.TargetInvocationException:调用目标抛出异常。 ---> System.Runtime.InteropServices.COMException: 旧格式或无效类型库。 (HRESULT 异常:0x80028018(TYPE_E_INVDATAREAD))“
应用程序对象似乎没有工作簿,还有其他问题。 我确定代码没问题,但也许我的 .Net 框架或办公版本或构建设置有问题? 任何人都可以对此有所了解吗?
** 编辑 1 **
因此,根据 Richard Morgan 的建议,我尝试了以下操作,发现原始代码运行时可能没有活动工作簿:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using Excel = Microsoft.Office.Interop.Excel;
using Office = Microsoft.Office.Core;
using Microsoft.Office.Tools.Excel;
namespace ExcelAddIn1
{
public partial class ThisAddIn
{
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
this.Application.WorkbookActivate += new Excel.AppEvents_WorkbookActivateEventHandler(WorkWithWorkbook);
}
private void WorkWithWorkbook(Microsoft.Office.Interop.Excel.Workbook workbook)
{
// Workbook has been opened. Do stuff here.
var app = Globals.ThisAddIn.Application;
Excel.Workbook wb = app.ThisWorkbook;
}
private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
{
}
#region VSTO generated code
private void InternalStartup()
{
this.Startup += new System.EventHandler(ThisAddIn_Startup);
this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
}
#endregion
}
}
因此,当执行 WorkWithWorkbook() 时,我希望有一个 ActiveWorkbook 可供参考。不幸的是,我仍然得到 COMException:
"Exception from HRESULT: 0x800A03EC".
进一步检查应用程序对象表明工作簿集合已部分填充,但许多属性仍引用:
System.Runtime.InteropServices.COMException - 旧格式或无效类型库
进一步搜索发现这可能是由于 Excel 和 VS code 之间的区域设置不匹配造成的,但我已经检查过在这种情况下区域是否匹配。
编辑 2
所以也许我在这里很愚蠢!进一步阅读表明,应用程序的 .ThisWorkbook 属性 returns 是对包含代码的工作簿的引用。由于这是一个加载项,因此代码包含在 .dll 中。因此,我使用了 .ActiveWorkbook,它返回了一个引用而没有抛出异常!
由于工作簿中不包含加载项代码,因此未设置 Application.ThisWorkbook
属性。 Application.ThisWorkbook
属性 用于return 对包含代码的工作簿的引用,并且不存在这样的工作簿!
为了获得对当前打开的工作簿的引用并导致代码被执行,应该改用 Application.ActiveWorkbook
引用。
奇怪的代码:
private void ThisAddIn_Startup(object sender, System.EventArgs e)
{
this.Application.WorkbookActivate += new Excel.AppEvents_WorkbookActivateEventHandler(WorkWithWorkbook);
}
private void WorkWithWorkbook(Microsoft.Office.Interop.Excel.Workbook workbook)
{
// Workbook has been opened. Do stuff here.
var app = Globals.ThisAddIn.Application;
Excel.Workbook wb = app.ThisWorkbook;
}
因此,Excel 为您提供刚刚激活的确切 Workbook
,然后您 运行 自己编写代码?!
对此要非常小心。
我们的 VSTO Excel 插件中的 ActiveWorkbook
和 ThisWorkbook
有问题,特别是当用户 "do something" 启动我们的 VSTO 代码时,但他们有其他问题Excel 个文件打开,或者我们的 VSTO 任务需要一些时间,同时它们切换到另一个工作簿。
确保代码处理正确文件的最佳(唯一?)方法是始终使用传递给 OnActivate
函数的 Workbook
。
private void WorkWithWorkbook(Microsoft.Office.Interop.Excel.Workbook workbook)
{
// Do some stuff directly with "workbook"
//
}
至于 0x800A03EC 错误,它似乎是 Excel 的通用 "this could mean anything" COM 错误之一。
我们在尝试计算我们应该使用哪个ExcelWorkbook
对象时也看到了它。