.NET

能够相对于父窗体居中的MessageBox对话框

2018-04-16  本文已影响9人  冰麟轻武

以前写的,最近用到了,搬运一下

/*
 * 名称:MessageBox
 * 依赖:无
 * 功能:MessageBox对话框,能够相对于父窗体居中
 * 作者:冰麟轻武
 * 日期:2011年5月18日
 * 版本:1.3
 * 最后更新:2018年4月6日
 */
using System;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Threading;
using System.Windows.Forms;
namespace 直接替换自己的命名空间
{
    /// <summary>
    /// MessageBox对话框,能够相对于父窗体居中
    /// </summary>
    public class MessageBox
    {
        public static DialogResult Show(string text)
        {
            Initialize();
            return System.Windows.Forms.MessageBox.Show(text);
        }
        public static DialogResult Show(string text, string caption)
        {
            Initialize();
            return System.Windows.Forms.MessageBox.Show(text, caption);
        }
        public static DialogResult Show(string text, string caption, MessageBoxButtons buttons)
        {
            var frm = Form.ActiveForm;
            _owner = frm.IsMdiContainer ? frm.ActiveMdiChild : frm;
            Initialize();
            return System.Windows.Forms.MessageBox.Show(text, caption, buttons);
        }
        public static DialogResult Show(string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon)
        {
            Initialize();
            return System.Windows.Forms.MessageBox.Show(text, caption, buttons, icon);
        }
        public static DialogResult Show(string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon, MessageBoxDefaultButton defButton)
        {
            Initialize();
            return System.Windows.Forms.MessageBox.Show(text, caption, buttons, icon, defButton);
        }
        public static DialogResult Show(string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon, MessageBoxDefaultButton defButton, MessageBoxOptions options)
        {
            Initialize();
            return System.Windows.Forms.MessageBox.Show(text, caption, buttons, icon, defButton, options);
        }
        public static DialogResult Show(IWin32Window owner, string text)
        {
            Initialize(owner);
            return System.Windows.Forms.MessageBox.Show(owner, text);
        }
        public static DialogResult Show(IWin32Window owner, string text, string caption)
        {
            Initialize(owner);
            return System.Windows.Forms.MessageBox.Show(owner, text, caption);
        }
        public static DialogResult Show(IWin32Window owner, string text, string caption, MessageBoxButtons buttons)
        {
            Initialize(owner);
            return System.Windows.Forms.MessageBox.Show(owner, text, caption, buttons);
        }
        public static DialogResult Show(IWin32Window owner, string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon)
        {
            Initialize(owner);
            return System.Windows.Forms.MessageBox.Show(owner, text, caption, buttons, icon);
        }
        public static DialogResult Show(IWin32Window owner, string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon, MessageBoxDefaultButton defButton)
        {
            Initialize(owner);
            return System.Windows.Forms.MessageBox.Show(owner, text, caption, buttons, icon, defButton);
        }
        public static DialogResult Show(IWin32Window owner, string text, string caption, MessageBoxButtons buttons, MessageBoxIcon icon, MessageBoxDefaultButton defButton, MessageBoxOptions options)
        {
            Initialize(owner);
            return System.Windows.Forms.MessageBox.Show(owner, text, caption, buttons, icon,
                                   defButton, options);
        }
        #region 私有API
        private static IWin32Window _owner;
        private static HookProc _hookProc;
        private static IntPtr _hHook;
        delegate IntPtr HookProc(int nCode, IntPtr wParam, IntPtr lParam);
        const int WH_CALLWNDPROCRET = 12;
        enum CbtHookAction : int
        {
            HCBT_MOVESIZE = 0,
            HCBT_MINMAX = 1,
            HCBT_QS = 2,
            HCBT_CREATEWND = 3,
            HCBT_DESTROYWND = 4,
            HCBT_ACTIVATE = 5,
            HCBT_CLICKSKIPPED = 6,
            HCBT_KEYSKIPPED = 7,
            HCBT_SYSCOMMAND = 8,
            HCBT_SETFOCUS = 9
        }
        [DllImport("user32.dll")]
        private static extern bool GetWindowRect(IntPtr hWnd, ref Rectangle lpRect);
        [DllImport("user32.dll")]
        private static extern int MoveWindow(IntPtr hWnd, int X, int Y, int nWidth, int nHeight, bool bRepaint);
        [DllImport("user32.dll")]
        static extern IntPtr SetWindowsHookEx(int idHook, HookProc lpfn, IntPtr hInstance, int threadId);
        [DllImport("user32.dll")]
        static extern int UnhookWindowsHookEx(IntPtr idHook);
        [DllImport("user32.dll")]
        static extern IntPtr CallNextHookEx(IntPtr idHook, int nCode, IntPtr wParam, IntPtr lParam);
        [StructLayout(LayoutKind.Sequential)]
        struct CWPRETSTRUCT
        {
            public IntPtr lResult;
            public IntPtr lParam;
            public IntPtr wParam;
            public uint message;
            public IntPtr hwnd;
        };
        static MessageBox()
        {
            _hookProc = new HookProc(MessageBoxHookProc);
            _hHook = IntPtr.Zero;
        }
        private static void Initialize(IWin32Window owner = null)
        {
            if (_hHook != IntPtr.Zero)
            {
                return;
            }
            if (owner == null)
            {
                _owner = Form.ActiveForm;
            }
            if (_owner is Form frm)
            {
                if (frm.Visible == false)
                {
                    _owner = null;
                }
                else if (frm.IsMdiContainer)
                {
                    _owner = frm.ActiveMdiChild;
                }
            }
            if (_owner != null)
            {
                _hHook = SetWindowsHookEx(WH_CALLWNDPROCRET, _hookProc, IntPtr.Zero, AppDomain.GetCurrentThreadId());
            }
            else
            {
                _hHook = IntPtr.Zero;
            }
        }
        private static IntPtr MessageBoxHookProc(int nCode, IntPtr wParam, IntPtr lParam)
        {
            if (nCode < 0)
            {
                return CallNextHookEx(_hHook, nCode, wParam, lParam);
            }
            var msg = (CWPRETSTRUCT)Marshal.PtrToStructure(lParam, typeof(CWPRETSTRUCT));
            var hook = _hHook;
            if (msg.message == (int)CbtHookAction.HCBT_ACTIVATE)
            {
                try
                {
                    CenterWindow(msg.hwnd);
                }
                finally
                {
                    UnhookWindowsHookEx(_hHook);
                    _hHook = IntPtr.Zero;
                }
            }
            return CallNextHookEx(hook, nCode, wParam, lParam);
        }
        private static void CenterWindow(IntPtr hChildWnd)
        {
            var recChild = new Rectangle(0, 0, 0, 0);
            var success = GetWindowRect(hChildWnd, ref recChild);
            var width = recChild.Width - recChild.X;
            var height = recChild.Height - recChild.Y;
            var recParent = new Rectangle(0, 0, 0, 0);
            success = GetWindowRect(_owner.Handle, ref recParent);
            var ptCenter = new Point(0, 0);
            ptCenter.X = recParent.X + ((recParent.Width - recParent.X) / 2);
            ptCenter.Y = recParent.Y + ((recParent.Height - recParent.Y) / 2);
            var ptStart = new Point(0, 0);
            ptStart.X = (ptCenter.X - (width / 2));
            ptStart.Y = (ptCenter.Y - (height / 2));
            ptStart.X = (ptStart.X < 0) ? 0 : ptStart.X;
            ptStart.Y = (ptStart.Y < 0) ? 0 : ptStart.Y;
            var result = MoveWindow(hChildWnd, ptStart.X, ptStart.Y, width,
                                    height, false);
        }
        #endregion
    }
}
上一篇下一篇

猜你喜欢

热点阅读