wpf 如何将 Window.Owner 设置为 Outlook 窗口

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/12733974/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-13 05:39:43  来源:igfitidea点击:

How to set the Window.Owner to Outlook window

c#.netwpfoutlookvsto

提问by Kumar

I have an outlook plugin which pops up a WPF window

我有一个弹出 WPF 窗口的 Outlook 插件

Is there a way to set the WPF's Window.Ownerproperty to Outlook?

有没有办法将 WPF 的Window.Owner属性设置为 Outlook?

回答by SliverNinja - MSFT

Kudos to @reedcopsey for putting us on the right track...

感谢@reedcopsey 让我们走上正轨......

The trick for retrieving the Outlook Handleis using reflection to obtain the active window's title (Caption) and the FindWindowWin32 API to obtain the active window IntPtrhandle (inspector, explorer, etc.). Inspired from this MSDN forum post. Once you have the active window handle, you can leverage WindowInteropHelperfor managing the owner relationship.

检索Outlook 句柄的技巧是使用反射获取活动窗口的标题 ( Caption) 和使用FindWindowWin32 API 获取活动窗口IntPtr句柄(检查器、资源管理器等)。灵感来自这个 MSDN 论坛帖子。一旦您拥有活动窗口句柄,您就可以利用它WindowInteropHelper来管理所有者关系。

Retrieving Outlook Handle (via ActiveWindow)

检索 Outlook 句柄(通过ActiveWindow

Window yourWPFWindow = new Window();
dynamic activeWindow = Globals.ThisAddIn.Application.ActiveWindow();
IntPtr outlookHwnd = new OfficeWin32Window(activeWindow).Handle;
WindowInteropHelper wih = new WindowInteropHelper(yourWPFWindow);
wih.Owner = outlookHwnd;
yourWPFWindow.Show();

OfficeWin32Window (Helper Class)

OfficeWin32Window(帮助类

///<summary>
/// This class retrieves the IWin32Window from the current active Office window.
/// This could be used to set the parent for Windows Forms and MessageBoxes.
///</summary>
///<example>
/// OfficeWin32Window parentWindow = new OfficeWin32Window (ThisAddIn.OutlookApplication.ActiveWindow ());   
/// MessageBox.Show (parentWindow, "This MessageBox doesn't go behind Outlook !!!", "Attention !", MessageBoxButtons.Ok , MessageBoxIcon.Question );
///</example>
public class OfficeWin32Window : IWin32Window
{

    ///<summary>
    /// The <b>FindWindow</b> method finds a window by it's classname and caption.
    ///</summary>
    ///<param name="lpClassName">The classname of the window (use Spy++)</param>
    ///<param name="lpWindowName">The Caption of the window.</param>
    ///<returns>Returns a valid window handle or 0.</returns>
    [DllImport("user32")]
    public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

    #region IWin32Window Members

    ///<summary>
    /// This holds the window handle for the found Window.
    ///</summary>
    IntPtr _windowHandle = IntPtr.Zero;

    ///<summary>
    /// The <b>Handle</b> of the Outlook WindowObject.
    ///</summary>
    public IntPtr Handle
    {
        get { return _windowHandle; }
    }

    #endregion

    ///<summary>
    /// The <b>OfficeWin32Window</b> class could be used to get the parent IWin32Window for Windows.Forms and MessageBoxes.
    ///</summary>
    ///<param name="windowObject">The current WindowObject.</param>
    public OfficeWin32Window(object windowObject)
    {
        string caption = windowObject.GetType().InvokeMember("Caption", System.Reflection.BindingFlags.GetProperty, null, windowObject, null).ToString();

        // try to get the HWND ptr from the windowObject / could be an Inspector window or an explorer window
        _windowHandle = FindWindow("rctrl_renwnd32
WindowInteropHelper wih = new WindowInteropHelper(yourWindow);
wih.Owner = outlookHwnd;
yourWindow.Show();
", caption); } }

回答by Reed Copsey

This can be done via WindowInteropHelper:

这可以通过WindowInteropHelper完成:

##代码##