【问题标题】:VSTO: Visual Studio designer reusing running Excel instance instead of starting its ownVSTO:Visual Studio 设计器重用正在运行的 Excel 实例,而不是启动它自己的实例
【发布时间】:2011-04-06 14:33:59
【问题描述】:

当您在 Visual Studio 中创建 VSTO 工作簿项目时,VS 会创建一个新的 Excel (xlsx) 文件并允许您直接在 Visual Studio 中进行编辑。 Excel 工作簿与任何代码或表单一起出现在新选项卡中:

为了支持这一点,Visual Studio 需要在设计时运行EXCEL.EXE 的实例。

问题是不幸的是,如果它发现一个已经在运行的实例,而不是总是运行它自己的实例,它将使用那个实例。因此,如果出于某种原因我的 PC 上已经打开了 Excel,Visual Studio 将重用该实例。

这会导致几个问题:如果 Excel 运行长时间计算,它将冻结 Visual Studio;如果在 VS 中打开一个模态 Excel 窗口(例如单元格或字体属性),它会冻结我现有的 Excel 窗口(VS 外部的那个)。如果 VS 崩溃,Excel.exe 仍然有项目的 excel 文件的句柄,但我无法杀死它,因为我在 Excel 中打开了其他文件。最后,如果我碰巧在 PC 上打开了 Excel 2003,并且我的项目正在使用 Excel 2007,VS 将仍然尝试使用当前正在运行的 2003 实例,然后在被询问时会感到困惑打开2007文件,尝试转换等,结果一团糟。

我找到的唯一解决方案是关闭所有EXCEL.EXE实例,只有在运行VS后,打开VSTO项目,VS会发现没有运行的excel实例并运行它自己的,然后我可以重新打开我的以前在我自己打开的新实例中打开的文件。虽然这并不总是可能的,而且可能真的很痛苦,所以我想找到一种方法让 VS 每次都打开它自己的个人新实例。

【问题讨论】:

    标签: c# excel vsto


    【解决方案1】:

    您是否尝试过在 VS 中更改项目的 DEBUG 选项以明确指向 Excel.exe 并在 excel 命令行上将项目命名为 XLSX 文件?

    这是我唯一能想到的尝试始终获得第二个 excel 实例的方法。

    Office 应用程序倾向于使用现有实例,因此这种行为并不让我感到惊讶。单词也可能很棘手。

    当您开始谈论在一台开发机器上加载多个版本的 Office 时(顺便说一句,我也是这样做的),事情很快就会变得非常奇怪。

    【讨论】:

    • 这又是在设计的时候。 DEBUG 配置无关紧要,因为它仅在我按 F5 compilerun 程序时使用。我遇到的问题是在我编译或运行任何东西之前,就在我在设计器中显示 Excel 工作表时(如屏幕截图所示)。
    【解决方案2】:

    这个简单的 C# 控制台应用程序可以打开一个空白的、不可见的 EXCEL.EXE 进程。您可以安排此程序在任何其他 Excel 实例启动之前登录时运行。

    using System;
    using System.Runtime.InteropServices;
    
    //C:\Program Files (x86)\Microsoft Visual Studio 11.0\Visual Studio Tools for
    //Office\PIA\Office14\Microsoft.Office.Interop.Excel.dll
    using Excel = Microsoft.Office.Interop.Excel; 
    
    class Program
    {
        [DllImport("kernel32.dll")]
        static extern IntPtr GetConsoleWindow();
    
        [DllImport("user32.dll")]
        static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);
    
        const int SW_HIDE = 0;
        const int SW_SHOW = 5;
    
        static void Main(string[] args)
        {
            Console.WriteLine("Opening new excel process...");
            var handle = GetConsoleWindow();
            ShowWindow(handle, SW_HIDE);
            try
            {
                Excel.Application Ea = new Excel.Application();
                Ea.Workbooks.Add();
                Ea.Visible = false;
            }
            catch (Exception exep)
            {
                Console.WriteLine(exep.Message);
                Console.ReadKey();
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-04-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-09-26
      • 2012-02-03
      相关资源
      最近更新 更多