【问题标题】:Strange behavior when showing WPF window in Outlook在 Outlook 中显示 WPF 窗口时的奇怪行为
【发布时间】:2013-01-21 10:36:02
【问题描述】:

我使用以下代码在 Outlook 的新消息窗口中显示我的 WPF 窗口:

private void DisplayWindow(Window window) {
    var wih = new System.Windows.Interop.WindowInteropHelper(window);
    wih.Owner = GetForegroundWindow();            
    window.ShowInTaskbar = false;            
    window.ShowDialog();
}

[DllImport("user32.dll")]
private static extern IntPtr GetForegroundWindow();

我的问题是,当 ToolTips 和 ComboBox 下拉菜单变得可见时,WPF 窗口会消失在新消息窗口的后面,只留下“弹出”内容在前面。谁能解释为什么会发生这种情况,以及托管窗口的正确方法可能是什么?

编辑:

只有在将收件人添加到“发送”框后才会发生这种情况,并且似乎只有在前台窗口是新的邮件消息窗口时才会出现问题。

复制:

将 Outlook 插件项目和 WPF 项目(面向 .NET 4.0)添加到新解决方案。

在 MainWindow.xaml 中放置一个包含一些项目的 ComboBox。

从 App.xaml 中删除 StartupUri 并将以下内容添加到 App.cs。

public void ShowWindow() {
    MainWindow window = new MainWindow();
    var wih = new System.Windows.Interop.WindowInteropHelper(window);
    wih.Owner = GetForegroundWindow();
    window.ShowInTaskbar = false;
    window.ShowDialog();
}

[DllImport("user32.dll")]
private static extern IntPtr GetForegroundWindow();

向 Outlook 项目添加对 WindowsBaseSystem.XamlPresentationFramework 的引用。

将功能区 (XML) 添加到 Outlook 项目,并在 .xml 中添加以下内容。

<customUI ...>
  <ribbon>
    <tabs>
      <tab idMso="TabNewMailMessage">
        <group id="MyGroup"
               insertAfterMso="GroupMailNew">
          <button id="myButton"
                  size="large"      
                  onAction="myButton_Action"
                  imageMso="HappyFace"/>
        </group>
      </tab>
    </tabs>
  </ribbon>
</customUI>

将以下内容添加到功能区代码中。

MyWpfApplication.App app;

public void Ribbon_Load(Office.IRibbonUI ribbonUI) {
    this.ribbon = ribbonUI;

    var appThread = new Thread(new ThreadStart(() => {
        this.app = new MyWpfApplication.App();
        app.ShutdownMode = System.Windows.ShutdownMode.OnExplicitShutdown;
        app.Run();
    }));
    appThread.SetApartmentState(ApartmentState.STA);
    appThread.Start();
}

public void myButton_Action(Office.IRibbonControl control) {

    // Dispatcher used as cross thread operation.
    app.Dispatcher.BeginInvoke((Action)(() => {
        app.ShowWindow();
    }));
}

将以下内容添加到 ThisAddIn

protected override Microsoft.Office.Core
        .IRibbonExtensibility CreateRibbonExtensibilityObject() {
    return new Ribbon();
}

运行 Outlook 插件,创建新邮件,添加收件人,然后单击笑脸按钮。当您点击ComboBox 时,您将看到该错误。

【问题讨论】:

  • 您是否尝试过 Winforms FormElementHost 用于您的 WPF 内容?
  • 您的目标是哪个版本的 Outlook?
  • 肯特 - 从我更新的问题中可以看出,这与我当前的设计不符。我想在后台线程中保留一个正在运行的 WPF 应用程序,并根据需要使用它的 Dispatcher 创建窗口。如果没有人有解决方案,我可能不得不考虑重组以使用 Winforms。

标签: wpf outlook window ms-office office-addins


【解决方案1】:

也许您遇到了臭名昭著的“空域”问题。请参阅hereherehere。人们寄予厚望,希望它会在 .NET 4.5 中得到修复,但遗憾的是,当 MS 宣布修复本身存在太多错误而无法发布时,这些都破灭了。

【讨论】:

    【解决方案2】:

    可能与此处描述的问题相同:

    The WPF dialog box disappears when it displays a tooltip or drop-down combo box in Windows 8 or Windows Server 2012

    .NET Framework 4.7.1 的源代码在System.Windows.FrameworkCompatibilityPreferences 类中有注释,说Windows 桌面窗口管理器中存在一个错误,在某些情况下会导致窗口的z 顺序不正确。

    建议的解决方法是将以下代码添加到 WPF 应用程序的 app.config 文件中:

    <?xml version="1.0" encoding="utf-8"?>
    <configuration>
      <appSettings>
      <add key="UseSetWindowPosForTopmostWindows" value="True" />
      </appSettings>
    </configuration>
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-12-03
      • 1970-01-01
      • 1970-01-01
      • 2011-10-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多