VSTO 加载项 CustomTaskPane 在升级到 Word 2016/2019 后自行打开

VSTO Add-In CustomTaskPane opens itself after upgrading to Word 2016/2019

我们通过 VSTOContrib.
开发了带有 CustomTaskPanes 和 MVVM 支持的 Word 2010 的 Word VSTO 加载项 升级到 Word 2016/2019 后,我们的 CustomTaskPanes 会随机显示,用户无需执行任何操作。 似乎 Word 在使用 CustomTaskPane 时会注意到并希望下次自动(重新)打开它。

例如,在打开 new/exisitng 文档时会打开 CustomTaskPane。不会那么糟糕,如果它不会出现故障(打开,关闭,打开,关闭,......)直到它关闭或保持打开状态。 如果 CustomTaskPane 保持打开状态,则它不可用,因为它没有由我们的加载项加载的 DataContext。

ThisAddIn 中的此代码 creates/removes CustomTaskPanes:

public CustomTaskPane AddTaskPane(UserControl userControl, string title, Window owner)
{
    return CustomTaskPanes.Add(userControl, title, owner);
}

public void RemoveTaskPane(CustomTaskPane taskPane)
{
    if (taskPane == null)
        return;

    CustomTaskPanes.Remove(taskPane);
}

RibbonViewModel(每个 Document/Window 的 ViewModel)这样调用代码。 _addInHelper 具有 creating/removing CustomTaskPanes 的事件以通过回调到达 ThisAddIn 代码和 returns CustomTaskPane 实例。它还使用 IoC 容器来解析视图 "CustomTaskPaneView".

// Gets called when a new Window opens or a new Document is opened
public override void Intialize(Document document) 
{
    // ...
    CreateCustomTaskPane();
    // ...
}

private void CreateCustomTaskPane()
{
    if (_customTaskPane != null)
        return;

    _addInHelper.AddTaskPane("CustomTaskPaneView", "Custom headline", CurrentWindow, result =>
    {
        _customTaskPane = result;
    });

    if (_customTaskPane == null)
    {
        _log.Error(...);
        return;
    }

    _customTaskPane.DockPositionRestrict = MsoCTPDockPositionRestrict.msoCTPDockPositionRestrictNoHorizontal;
    _customTaskPane.Width = Settings.Default.TaskPaneWidth;
    _customTaskPane.DockPosition = Settings.Default.TaskPanePosition;

    // TaskPane height and width are saved seperately for DockPositionFloating
    if (_customTaskPane.DockPosition != MsoCTPDockPosition.msoCTPDockPositionFloating)
    {
        // Set height and width for DockPositionFloating.
        // If the user drags the TaskPane to Floating, it will have the correct size.
        var oldDockPosition = _customTaskPane.DockPosition;

        _customTaskPane.DockPosition = MsoCTPDockPosition.msoCTPDockPositionFloating;
        _customTaskPane.Height = Settings.Default.TaskPaneHeight;
        _customTaskPane.Width = Settings.Default.TaskPaneWidth;
        _customTaskPane.DockPosition = oldDockPosition;
    }
    else
    {
        _customTaskPane.Height = Settings.Default.TaskPaneHeight;
        _customTaskPane.Width = Settings.Default.TaskPaneWidth;
    }

    // Saving/updating settings in these
    _customTaskPane.VisibleChanged += ContentControlsTaskPane_OnVisibleChanged;
    _customTaskPane.DockPositionChanged += ContentControlsTaskPane_OnDockPositionChanged;
}

关闭Window/Document时调用这段代码:

public override void Cleanup()
{
    if (_customTaskPane != null)
    {
        SaveCustomTaskPaneProperties();

        _contentControlsTaskPane.VisibleChanged -= ContentControlsTaskPane_OnVisibleChanged;
        _contentControlsTaskPane.DockPositionChanged -= ContentControlsTaskPane_OnDockPositionChanged;

        // Checks if the COM Object was cleaned up already
        if (!_contentControlsTaskPane.IsDisposed())
        {
            // Tried to manually close the CustomTaskPane, but didn't help either
            if (_contentControlsTaskPane.Visible)
                _contentControlsTaskPane.Visible = false;

            // Cleanup the CustomTaskPane ViewModel instance
            var taskPaneViewModel = _contentControlsTaskPane.GetViewModel();
            taskPaneViewModel?.Dispose();

            _addInHelper.RemoveTaskPane(_contentControlsTaskPane);
        }
    }
}

这仅在使用 Word 2016 和 2019(我们不使用 2013)时发生,而在 Word 2010 中根本不会发生。 在出于测试目的将 VSTO 项目升级到 VSTO 加载项 2013 和 2016 后,它并没有变得更好。

示例:

我没有找到任何可能导致此问题的 Word 选项。 知道这可能导致什么以及如何解决这个问题/获得解决方法吗?


编辑
这是更新后的代码示例WordTaskPanesBug

重现步骤:

  1. 启动 Word/运行 项目
  2. 单击 "Open" 按钮
  3. 单击 "New document" 按钮
  4. 单击 "New document" 按钮,任务窗格打开(但这次不会出现故障)

CustomTaskPane 在示例项目中关闭文档时也会出现故障,但在我们的真实项目中不会。

Old example gif

我添加了索引来指示正在显示哪个任务窗格,这表明第二次创建新文档时添加的任务窗格来自第一个文档(创建新文档时关闭的那个)第一次,可能是因为它是空的)。

我认为您 运行 遇到的问题是这个:Creating and managing custom task panes for multiple documents in a VSTO Word addin